mirror of
git://sourceware.org/git/glibc.git
synced 2024-11-21 01:12:26 +08:00
Update.
1998-07-24 21:29 Ulrich Drepper <drepper@cygnus.com> * nscd/connections.c (pw_send_answer): Make one single writev call. (gr_send_answer): Do the work in two writev calls. This change changes the protocol. * nscd/nscd_getgr_r.c (__nscd_getgr_r): Adjust for protocol change. We now can do the job using two readv calls.
This commit is contained in:
parent
6c202c6870
commit
264d5b944d
@ -1,3 +1,12 @@
|
||||
1998-07-24 21:29 Ulrich Drepper <drepper@cygnus.com>
|
||||
|
||||
* nscd/connections.c (pw_send_answer): Make one single writev call.
|
||||
(gr_send_answer): Do the work in two writev calls. This change
|
||||
changes the protocol.
|
||||
|
||||
* nscd/nscd_getgr_r.c (__nscd_getgr_r): Adjust for protocol change.
|
||||
We now can do the job using two readv calls.
|
||||
|
||||
1998-07-24 Ulrich Drepper <drepper@cygnus.com>
|
||||
|
||||
* sysdeps/generic/glob.c (glob): Fix problems with handle tilde.
|
||||
|
@ -157,7 +157,7 @@ handle_new_request (int **connp, request_header **reqp, char **key)
|
||||
read_polls[i].fd = -1;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (found == 0)
|
||||
{
|
||||
dbg_log (_("No sockets with data found !"));
|
||||
@ -320,7 +320,10 @@ init_sockets (void)
|
||||
void
|
||||
pw_send_answer (int conn, struct passwd *pwd)
|
||||
{
|
||||
struct iovec vec[6];
|
||||
pw_response_header resp;
|
||||
size_t total_len;
|
||||
int nblocks;
|
||||
|
||||
resp.version = NSCD_VERSION;
|
||||
if (pwd != NULL)
|
||||
@ -352,40 +355,42 @@ pw_send_answer (int conn, struct passwd *pwd)
|
||||
return;
|
||||
}
|
||||
|
||||
/* Send response header. */
|
||||
if (write (sock[conn], &resp, sizeof (pw_response_header)) !=
|
||||
sizeof (pw_response_header))
|
||||
{
|
||||
dbg_log (_("write incomplete on send response: %s"), strerror (errno));
|
||||
return;
|
||||
}
|
||||
/* Add response header. */
|
||||
vec[0].iov_base = &resp;
|
||||
vec[0].iov_len = sizeof (pw_response_header);
|
||||
total_len = sizeof (pw_response_header);
|
||||
nblocks = 1;
|
||||
|
||||
if (resp.found)
|
||||
{
|
||||
struct iovec vec[5];
|
||||
/* Add pw_name. */
|
||||
vec[1].iov_base = pwd->pw_name;
|
||||
vec[1].iov_len = resp.pw_name_len;
|
||||
total_len += resp.pw_name_len;
|
||||
/* Add pw_passwd. */
|
||||
vec[2].iov_base = pwd->pw_passwd;
|
||||
vec[2].iov_len = resp.pw_passwd_len;
|
||||
total_len += resp.pw_passwd_len;
|
||||
/* Add pw_gecos. */
|
||||
vec[3].iov_base = pwd->pw_gecos;
|
||||
vec[3].iov_len = resp.pw_gecos_len;
|
||||
total_len += resp.pw_gecos_len;
|
||||
/* Add pw_dir. */
|
||||
vec[4].iov_base = pwd->pw_dir;
|
||||
vec[4].iov_len = resp.pw_dir_len;
|
||||
total_len += resp.pw_dir_len;
|
||||
/* Add pw_shell. */
|
||||
vec[5].iov_base = pwd->pw_shell;
|
||||
vec[5].iov_len = resp.pw_shell_len;
|
||||
total_len += resp.pw_shell_len;
|
||||
|
||||
/* Send pw_name. */
|
||||
vec[0].iov_base = pwd->pw_name;
|
||||
vec[0].iov_len = resp.pw_name_len;
|
||||
/* Send pw_passwd. */
|
||||
vec[1].iov_base = pwd->pw_passwd;
|
||||
vec[1].iov_len = resp.pw_passwd_len;
|
||||
/* Send pw_gecos. */
|
||||
vec[2].iov_base = pwd->pw_gecos;
|
||||
vec[2].iov_len = resp.pw_gecos_len;
|
||||
/* Send pw_dir. */
|
||||
vec[3].iov_base = pwd->pw_dir;
|
||||
vec[3].iov_len = resp.pw_dir_len;
|
||||
/* Send pw_shell. */
|
||||
vec[4].iov_base = pwd->pw_shell;
|
||||
vec[4].iov_len = resp.pw_shell_len;
|
||||
|
||||
if (writev (sock[conn], vec, 5) != (resp.pw_name_len + resp.pw_passwd_len
|
||||
+ resp.pw_gecos_len + resp.pw_dir_len
|
||||
+ resp.pw_shell_len))
|
||||
dbg_log (_("write incomplete on send passwd answer: %s"),
|
||||
strerror (errno));
|
||||
nblocks = 6;
|
||||
}
|
||||
|
||||
/* Send all the data. */
|
||||
if (writev (sock[conn], vec, nblocks) != total_len)
|
||||
dbg_log (_("write incomplete on send passwd answer: %s"),
|
||||
strerror (errno));
|
||||
}
|
||||
|
||||
void
|
||||
@ -419,7 +424,11 @@ pw_send_disabled (int conn)
|
||||
void
|
||||
gr_send_answer (int conn, struct group *grp)
|
||||
{
|
||||
struct iovec *vec;
|
||||
size_t *len;
|
||||
gr_response_header resp;
|
||||
size_t total_len;
|
||||
int nblocks;
|
||||
|
||||
resp.version = NSCD_VERSION;
|
||||
if (grp != NULL)
|
||||
@ -447,54 +456,55 @@ gr_send_answer (int conn, struct group *grp)
|
||||
return;
|
||||
}
|
||||
|
||||
/* Send response header. */
|
||||
if (write (sock[conn], &resp, sizeof (gr_response_header))
|
||||
!= sizeof (gr_response_header))
|
||||
{
|
||||
dbg_log (_("write incomplete on send response: %s"), strerror (errno));
|
||||
return;
|
||||
}
|
||||
/* We have no fixed number of records so allocate the IOV here. */
|
||||
vec = alloca ((3 + 1 + resp.gr_mem_len) * sizeof (struct iovec));
|
||||
len = alloca (resp.gr_mem_len * sizeof (size_t));
|
||||
|
||||
/* Add response header. */
|
||||
vec[0].iov_base = &resp;
|
||||
vec[0].iov_len = sizeof (gr_response_header);
|
||||
total_len = sizeof (gr_response_header);
|
||||
nblocks = 1;
|
||||
|
||||
if (resp.found)
|
||||
{
|
||||
unsigned int l = 0;
|
||||
|
||||
/* Send gr_name. */
|
||||
if (write (sock[conn], grp->gr_name, resp.gr_name_len)
|
||||
!= resp.gr_name_len)
|
||||
{
|
||||
dbg_log (_("write incomplete on send response: %s"),
|
||||
strerror (errno));
|
||||
return;
|
||||
}
|
||||
/* Send gr_passwd. */
|
||||
if (write (sock[conn], grp->gr_passwd, resp.gr_passwd_len)
|
||||
!= resp.gr_passwd_len)
|
||||
{
|
||||
dbg_log (_("write incomplete on send response: %s"),
|
||||
strerror (errno));
|
||||
return;
|
||||
}
|
||||
/* Add gr_name. */
|
||||
vec[1].iov_base = grp->gr_name;
|
||||
vec[1].iov_len = resp.gr_name_len;
|
||||
total_len += resp.gr_name_len;
|
||||
/* Add gr_passwd. */
|
||||
vec[2].iov_base = grp->gr_passwd;
|
||||
vec[2].iov_len = resp.gr_passwd_len;
|
||||
total_len += resp.gr_passwd_len;
|
||||
nblocks = 3;
|
||||
|
||||
while (grp->gr_mem[l])
|
||||
if (grp->gr_mem[l])
|
||||
{
|
||||
size_t len = strlen (grp->gr_mem[l]);
|
||||
vec[3].iov_base = len;
|
||||
vec[3].iov_len = resp.gr_mem_len * sizeof (size_t);
|
||||
total_len += resp.gr_mem_len * sizeof (size_t);
|
||||
nblocks = 4;
|
||||
|
||||
if (write (sock[conn], &len, sizeof (len)) != sizeof (len))
|
||||
do
|
||||
{
|
||||
dbg_log (_("write incomplete on send response: %s"),
|
||||
strerror (errno));
|
||||
return;
|
||||
len[l] = strlen (grp->gr_mem[l]);
|
||||
|
||||
vec[nblocks].iov_base = grp->gr_mem[l];
|
||||
vec[nblocks].iov_len = len[l];
|
||||
total_len += len[l];
|
||||
|
||||
++nblocks;
|
||||
}
|
||||
if (write (sock[conn], grp->gr_mem[l], len) != len)
|
||||
{
|
||||
dbg_log (_("write incomplete on send response: %s"),
|
||||
strerror (errno));
|
||||
return;
|
||||
}
|
||||
++l;
|
||||
while (grp->gr_mem[++l]);
|
||||
}
|
||||
}
|
||||
|
||||
/* Send all the data. */
|
||||
if (writev (sock[conn], vec, nblocks) != total_len)
|
||||
dbg_log (_("write incomplete on send group answer: %s"),
|
||||
strerror (errno));
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -24,6 +24,7 @@
|
||||
#include <string.h>
|
||||
#include <unistd.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/uio.h>
|
||||
#include <sys/un.h>
|
||||
|
||||
#include "nscd.h"
|
||||
@ -139,83 +140,103 @@ __nscd_getgr_r (const char *key, request_type type, struct group *resultbuf,
|
||||
|
||||
if (gr_resp.found == 1)
|
||||
{
|
||||
size_t i;
|
||||
struct iovec *vec;
|
||||
size_t *len;
|
||||
char *p = buffer;
|
||||
int nblocks;
|
||||
size_t total_len;
|
||||
uintptr_t align;
|
||||
|
||||
if (buflen < gr_resp.gr_name_len + 1)
|
||||
/* A first check whether the buffer is sufficently large is possible. */
|
||||
if (buflen < gr_resp.gr_name_len + 1 + gr_resp.gr_passwd_len + 1)
|
||||
{
|
||||
__set_errno (ERANGE);
|
||||
__close (sock);
|
||||
return -1;
|
||||
}
|
||||
resultbuf->gr_name = p;
|
||||
|
||||
/* Allocate the IOVEC. */
|
||||
vec = alloca ((2 + gr_resp.gr_mem_len) * sizeof (struct iovec));
|
||||
len = alloca (gr_resp.gr_mem_len * sizeof (size_t));
|
||||
|
||||
vec[0].iov_base = resultbuf->gr_name = p;
|
||||
vec[0].iov_len = gr_resp.gr_name_len;
|
||||
total_len = gr_resp.gr_name_len;
|
||||
p += gr_resp.gr_name_len + 1;
|
||||
buflen -= (gr_resp.gr_name_len + 1);
|
||||
nbytes = __read (sock, resultbuf->gr_name, gr_resp.gr_name_len);
|
||||
if (nbytes != gr_resp.gr_name_len)
|
||||
{
|
||||
__close (sock);
|
||||
return 1;
|
||||
}
|
||||
resultbuf->gr_name[gr_resp.gr_name_len] = '\0';
|
||||
|
||||
if (buflen < gr_resp.gr_passwd_len + 1)
|
||||
{
|
||||
__set_errno (ERANGE);
|
||||
__close (sock);
|
||||
return -1;
|
||||
}
|
||||
resultbuf->gr_passwd = p;
|
||||
vec[1].iov_base = resultbuf->gr_passwd = p;
|
||||
vec[1].iov_len = gr_resp.gr_passwd_len;
|
||||
total_len += gr_resp.gr_passwd_len;
|
||||
p += gr_resp.gr_passwd_len + 1;
|
||||
buflen -= (gr_resp.gr_passwd_len + 1);
|
||||
nbytes = __read (sock, resultbuf->gr_passwd, gr_resp.gr_passwd_len);
|
||||
if (nbytes != gr_resp.gr_passwd_len)
|
||||
buflen -= total_len;
|
||||
nblocks = 2;
|
||||
|
||||
if (gr_resp.gr_mem_len > 0)
|
||||
{
|
||||
vec[2].iov_base = len;
|
||||
vec[2].iov_len = gr_resp.gr_mem_len * sizeof (size_t);
|
||||
total_len += gr_resp.gr_mem_len * sizeof (size_t);
|
||||
nblocks = 3;
|
||||
}
|
||||
|
||||
/* Get this data. */
|
||||
if (__readv (sock, vec, nblocks) != total_len)
|
||||
{
|
||||
__close (sock);
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* Now we know the sizes. First terminate the strings we just read. */
|
||||
resultbuf->gr_name[gr_resp.gr_name_len] = '\0';
|
||||
resultbuf->gr_passwd[gr_resp.gr_passwd_len] = '\0';
|
||||
|
||||
resultbuf->gr_gid = gr_resp.gr_gid;
|
||||
|
||||
if (buflen < ((gr_resp.gr_mem_len + 1) * sizeof (char *)))
|
||||
/* Now allocate the buffer the array for the group members. We must
|
||||
align the pointer. */
|
||||
align = ((__alignof__ (char *) - (p - ((char *) 0)))
|
||||
& (__alignof__ (char *) - 1));
|
||||
if (align + (1 + gr_resp.gr_mem_len) * sizeof (char *) > buflen)
|
||||
{
|
||||
__set_errno (ERANGE);
|
||||
__close (sock);
|
||||
return -1;
|
||||
}
|
||||
resultbuf->gr_mem = (char **)p;
|
||||
p += ((gr_resp.gr_mem_len + 1) * sizeof (char *));
|
||||
buflen -= ((gr_resp.gr_mem_len + 1) * sizeof (char *));
|
||||
p += align;
|
||||
resultbuf->gr_mem = (char **) p;
|
||||
p += (1 + gr_resp.gr_mem_len) * sizeof (char *);
|
||||
buflen -= align + (1 + gr_resp.gr_mem_len) * sizeof (char *);
|
||||
|
||||
resultbuf->gr_mem[gr_resp.gr_mem_len] = NULL;
|
||||
|
||||
for (i = 0; i < gr_resp.gr_mem_len; ++i)
|
||||
if (gr_resp.gr_mem_len > 0)
|
||||
{
|
||||
size_t len;
|
||||
nbytes = __read (sock, &len, sizeof (len));
|
||||
if (nbytes != sizeof (len))
|
||||
/* Prepare reading the group members. */
|
||||
size_t i;
|
||||
|
||||
total_len = 0;
|
||||
for (i = 0; i < gr_resp.gr_mem_len; ++i)
|
||||
{
|
||||
__close (sock);
|
||||
return 1;
|
||||
if (len[i] >= buflen)
|
||||
{
|
||||
__set_errno (ERANGE);
|
||||
__close (sock);
|
||||
return -1;
|
||||
}
|
||||
|
||||
vec[i].iov_base = resultbuf->gr_mem[i] = p;
|
||||
vec[i].iov_len = len[i];
|
||||
total_len += len[i];
|
||||
buflen -= len[i];
|
||||
p += len[i];
|
||||
*p++ = '\0';
|
||||
}
|
||||
|
||||
if (buflen < (len + 1))
|
||||
if (__readv (sock, vec, gr_resp.gr_mem_len) != total_len)
|
||||
{
|
||||
__set_errno (ERANGE);
|
||||
__close (sock);
|
||||
return -1;
|
||||
}
|
||||
resultbuf->gr_mem[i] = p;
|
||||
p += len + 1;
|
||||
buflen -= (len + 1);
|
||||
nbytes = __read (sock, resultbuf->gr_mem[i], len);
|
||||
resultbuf->gr_mem[i][len] = '\0';
|
||||
if (nbytes != len)
|
||||
{
|
||||
__close (sock);
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
__close (sock);
|
||||
return 0;
|
||||
|
Loading…
Reference in New Issue
Block a user