diff options
author | George McCollister <georgem@novatech-llc.com> | 2010-03-04 09:41:33 -0600 |
---|---|---|
committer | Stephen Gallagher <sgallagh@redhat.com> | 2010-03-08 13:42:46 -0500 |
commit | 8ad7891f28c0ffd991c51f2d64c32cf04c9ddbbc (patch) | |
tree | 6e6e8d8a8ad4e6e4b185b1aeeff2fdce0d943b90 /src/sss_client | |
parent | 7d83d46ff9eb06b294c186a41ad9e7dbe648f5c3 (diff) | |
download | sssd-8ad7891f28c0ffd991c51f2d64c32cf04c9ddbbc.tar.gz sssd-8ad7891f28c0ffd991c51f2d64c32cf04c9ddbbc.tar.bz2 sssd-8ad7891f28c0ffd991c51f2d64c32cf04c9ddbbc.zip |
Fixed alignment problems in nss client/server
I fixed a handful of alignment problems in sss_client and nss responder.
Enumerating group and passwd with getgrent and getpwent now works correctly
on ARM.
Signed-off-by: George McCollister <georgem@novatech-llc.com>
Diffstat (limited to 'src/sss_client')
-rw-r--r-- | src/sss_client/group.c | 18 | ||||
-rw-r--r-- | src/sss_client/passwd.c | 7 | ||||
-rw-r--r-- | src/sss_client/sss_cli.h | 14 |
3 files changed, 32 insertions, 7 deletions
diff --git a/src/sss_client/group.c b/src/sss_client/group.c index 675b8b71..e1b36e2a 100644 --- a/src/sss_client/group.c +++ b/src/sss_client/group.c @@ -78,17 +78,19 @@ struct sss_nss_gr_rep { static int sss_nss_getgr_readrep(struct sss_nss_gr_rep *pr, uint8_t *buf, size_t *len) { - size_t i, l, slen, ptmem; + size_t i, l, slen, ptmem, pad; ssize_t dlen; char *sbuf; uint32_t mem_num; + uint32_t c; if (*len < 11) { /* not enough space for data, bad packet */ return EBADMSG; } - pr->result->gr_gid = ((uint32_t *)buf)[0]; - mem_num = ((uint32_t *)buf)[1]; + SAFEALIGN_COPY_UINT32(&c, buf, NULL); + pr->result->gr_gid = c; + SAFEALIGN_COPY_UINT32(&mem_num, buf+sizeof(uint32_t), NULL); sbuf = (char *)&buf[8]; slen = *len - 8; @@ -127,9 +129,15 @@ static int sss_nss_getgr_readrep(struct sss_nss_gr_rep *pr, i++; dlen--; + /* Make sure pr->buffer[i+pad] is 32 bit aligned */ + pad = 0; + while((i + pad) % 4) { + pad++; + } + /* now members */ - pr->result->gr_mem = (char **)&(pr->buffer[i]); - ptmem = sizeof(char *) * (mem_num + 1); + pr->result->gr_mem = (char **)&(pr->buffer[i+pad]); + ptmem = (sizeof(char *) * (mem_num + 1)) + pad; if (ptmem > dlen) { return ERANGE; /* not ENOMEM, ERANGE is what glibc looks for */ } diff --git a/src/sss_client/passwd.c b/src/sss_client/passwd.c index 0d70b684..aa5c7602 100644 --- a/src/sss_client/passwd.c +++ b/src/sss_client/passwd.c @@ -74,13 +74,16 @@ static int sss_nss_getpw_readrep(struct sss_nss_pw_rep *pr, { size_t i, slen, dlen; char *sbuf; + uint32_t c; if (*len < 13) { /* not enough space for data, bad packet */ return EBADMSG; } - pr->result->pw_uid = ((uint32_t *)buf)[0]; - pr->result->pw_gid = ((uint32_t *)buf)[1]; + SAFEALIGN_COPY_UINT32(&c, buf, NULL); + pr->result->pw_uid = c; + SAFEALIGN_COPY_UINT32(&c, buf+sizeof(uint32_t), NULL); + pr->result->pw_gid = c; sbuf = (char *)&buf[8]; slen = *len - 8; diff --git a/src/sss_client/sss_cli.h b/src/sss_client/sss_cli.h index 1953db2f..2edd158d 100644 --- a/src/sss_client/sss_cli.h +++ b/src/sss_client/sss_cli.h @@ -408,6 +408,20 @@ int sss_pam_make_request(enum sss_cli_command cmd, uint8_t **repbuf, size_t *replen, int *errnop); +#ifndef SAFEALIGN_COPY_UINT32 +static inline void +safealign_memcpy(void *dest, const void *src, size_t n, size_t *counter) +{ + memcpy(dest, src, n); + if (counter) { + *counter += n; + } +} + +#define SAFEALIGN_COPY_UINT32(dest, src, pctr) \ + safealign_memcpy(dest, src, sizeof(uint32_t), pctr) +#endif + #endif /* _SSSCLI_H */ #if 0 |