apps/fsutils/passwd: Fix numerous errors found during testing

This commit is contained in:
Gregory Nutt 2016-01-20 09:36:07 -06:00
parent 06f9487838
commit 5aa177e03b
6 changed files with 91 additions and 21 deletions

View file

@ -55,6 +55,8 @@
* then this function will fail with -EEXIST.
*
* Input Parameters:
* username - Identifies the user to be added
* password - The password for the new user
*
* Returned Value:
* Zero (OK) is returned on success; a negated errno value is returned on

View file

@ -77,7 +77,7 @@ int passwd_append(FAR const char *username, FAR const char *password)
/* Append the new user record to the end of the password file */
stream = fopen(CONFIG_FSUTILS_PASSWD_PATH, "at");
stream = fopen(CONFIG_FSUTILS_PASSWD_PATH, "a");
if (stream == NULL)
{
int errcode = errno;

View file

@ -76,14 +76,18 @@ static int passwd_copyfile(FAR char *iobuffer, FILE *instream,
size_t nbytes;
size_t gulpsize;
size_t ncopied;
size_t remaining;
bool eof;
/* Copy 'offset' bytes from the instream to the outstream */
for (ncopied = 0; ncopied < copysize; ncopied += nwritten)
for (ncopied = 0, remaining = copysize, eof = false;
ncopied < copysize && !eof;
ncopied += nwritten)
{
/* How big of a gulp can we take on this pass through the loop */
gulpsize = copysize;
gulpsize = remaining;
if (gulpsize > CONFIG_FSUTILS_PASSWD_IOBUFFER_SIZE)
{
gulpsize = CONFIG_FSUTILS_PASSWD_IOBUFFER_SIZE;
@ -98,24 +102,56 @@ static int passwd_copyfile(FAR char *iobuffer, FILE *instream,
do
{
nxfrd = fread(buffer, 1, nbytes, instream);
if (nxfrd < 0)
if (nxfrd == 0)
{
int errcode = errno;
DEBUGASSERT(errcode > 0);
/* Zero is returned on either a read error or end-of-file */
if (errcode != EINTR)
if (ferror(instream))
{
return -errcode;
/* Read error */
int errcode = errno;
DEBUGASSERT(errcode > 0);
if (errcode != EINTR)
{
return -errcode;
}
}
else
{
/* End of file encountered.
*
* This occurs normally when copying to the end-of-the file.
* In that case, the caller just sticks a huge number in for
* copysize and lets the end-of-file indication terminate the
* copy.
*/
eof = true;
/* Was anything buffered on this pass? */
if (nread == 0)
{
/* No.. then we can just return success now */
return OK;
}
}
}
else
{
DEBUGASSERT(nxfrd > 0);
/* Update counters and pointers for successful read */
nread += nxfrd;
buffer += nxfrd;
nbytes -= nxfrd;
}
}
while (nread < gulpsize);
while (nread < gulpsize && !eof);
/* Write the buffer of data to outstream */
@ -125,9 +161,11 @@ static int passwd_copyfile(FAR char *iobuffer, FILE *instream,
do
{
nxfrd = fwrite(buffer, 1, nbytes, instream);
if (nxfrd < 0)
nxfrd = fwrite(buffer, 1, nbytes, outstream);
if (nxfrd == 0)
{
/* Write error */
int errcode = errno;
DEBUGASSERT(errcode > 0);
@ -138,13 +176,18 @@ static int passwd_copyfile(FAR char *iobuffer, FILE *instream,
}
else
{
DEBUGASSERT(nxfrd > 0);
/* Update counters and pointers for successful write */
nwritten += nxfrd;
buffer += nxfrd;
nbytes -= nxfrd;
}
}
while (nwritten < nread);
copysize -= nwritten;
remaining -= nwritten;
}
return OK;
@ -185,7 +228,8 @@ int passwd_delete(off_t offset)
/* Rename the /set/password file */
ret = rename(CONFIG_FSUTILS_PASSWD_PATH, CONFIG_FSUTILS_PASSWD_PATH ".tmp");
ret = rename(CONFIG_FSUTILS_PASSWD_PATH,
CONFIG_FSUTILS_PASSWD_PATH ".tmp");
if (ret < 0)
{
ret = -errno;
@ -197,15 +241,15 @@ int passwd_delete(off_t offset)
* writing.
*/
instream = fopen(CONFIG_FSUTILS_PASSWD_PATH ".tmp", "rt");
instream = fopen(CONFIG_FSUTILS_PASSWD_PATH ".tmp", "r");
if (instream == NULL)
{
ret = -errno;
DEBUGASSERT(ret < 0);
goto errout_with_iobuffer;
goto errout_with_tmpfile;
}
outstream = fopen(CONFIG_FSUTILS_PASSWD_PATH, "wt");
outstream = fopen(CONFIG_FSUTILS_PASSWD_PATH, "w");
if (outstream == NULL)
{
ret = -errno;
@ -259,6 +303,22 @@ errout_with_outstream:
errout_with_instream:
(void)fclose(instream);
errout_with_tmpfile:
if (ret < 0)
{
/* Restore the previous /etc/passwd file */
(void)unlink(CONFIG_FSUTILS_PASSWD_PATH);
(void)rename(CONFIG_FSUTILS_PASSWD_PATH ".tmp",
CONFIG_FSUTILS_PASSWD_PATH);
}
else
{
/* Delete the previous /etc/passwd file */
(void)unlink(CONFIG_FSUTILS_PASSWD_PATH ".tmp");
}
errout_with_iobuffer:
free(iobuffer);
return ret;

View file

@ -55,6 +55,7 @@
* not exist, then this function will fail.
*
* Input Parameters:
* username - Identifies the user to be deleted
*
* Returned Value:
* Zero (OK) is returned on success; a negated errno value is returned on
@ -62,7 +63,7 @@
*
****************************************************************************/
int passwd_deluser(FAR const char *username, FAR const char *password)
int passwd_deluser(FAR const char *username)
{
struct passwd_s passwd;
FAR sem_t *sem;

View file

@ -85,12 +85,12 @@ int passwd_find(FAR const char *username, FAR struct passwd_s *passwd)
/* Open the password file for reading */
stream = fopen(CONFIG_FSUTILS_PASSWD_PATH, "at");
stream = fopen(CONFIG_FSUTILS_PASSWD_PATH, "r");
if (stream == NULL)
{
int errcode = errno;
DEBUGASSERT(errcode > 0);
return errcode;
return -errcode;
}
/* Read the password file line by line until the record with the matching
@ -132,7 +132,7 @@ int passwd_find(FAR const char *username, FAR struct passwd_s *passwd)
{
/* We have a match, skip over any whitespace after the user name */
for (src = iobuffer; *src && isspace((int)*src); src++);
for (; *src && isspace((int)*src); src++);
if (*src == '\0')
{
/* Bad file format? */

View file

@ -54,6 +54,8 @@
* then this function will fail with -EEXIST.
*
* Input Parameters:
* username - Identifies the user to be added
* password - The password for the new user
*
* Returned Value:
* Zero (OK) is returned on success; a negated errno value is returned on
@ -71,6 +73,7 @@ int passwd_adduser(FAR const char *username, FAR const char *password);
* not exist, then this function will fail.
*
* Input Parameters:
* username - Identifies the user to be deleted
*
* Returned Value:
* Zero (OK) is returned on success; a negated errno value is returned on
@ -78,7 +81,7 @@ int passwd_adduser(FAR const char *username, FAR const char *password);
*
****************************************************************************/
int passwd_deluser(FAR const char *username, FAR const char *password);
int passwd_deluser(FAR const char *username);
/****************************************************************************
* Name: passwd_update
@ -88,6 +91,8 @@ int passwd_deluser(FAR const char *username, FAR const char *password);
* then this function will fail.
*
* Input Parameters:
* username - Identifies the user whose password will be updated
* password - The new password for the existing user
*
* Returned Value:
* Zero (OK) is returned on success; a negated errno value is returned on
@ -105,6 +110,8 @@ int passwd_update(FAR const char *username, FAR const char *password);
* password matches the user password in that faile.
*
* Input Parameters:
* username - Identifies the user whose password will be verified
* password - The password to be verified
*
* Returned Value:
* One (1) is returned on success match, Zero (OK) is returned on an