Hi,

[hopefully this mail is under ml size limit]

These six patches make uclibc malloc big(ger) buffers instead of
keeping them in data/bss - should help NOMMU people.

patch #1: introduce __uc_malloc, so that users can intercept OOM.
patch #2: convert des.c to use __uc_malloc (-70 kbytes of bss)
patch #3: convert resolv.c
patch #4: convert pwd_grp.c
patch #5: convert utent.c, getpass.c
patch #6: convert getnetent.c, md5.c

This deals with almost all buffers bigger than 100 bytes.
We pay in code size for that (+20 - +40 bytes per module
on i386):

    text data   bss   dec   hex filename
-    584    8   384   976   3d0 utent.o
+    611    8     4   623   26f utent.o
-     38    0   288   326   146 fgetgrent.o
+     63    0     4    67    43 fgetgrent.o
-     38    0   288   326   146 fgetpwent.o
+     63    0     4    67    43 fgetpwent.o
-     38    0   320   358   166 fgetspent.o
+     63    0     4    67    43 fgetspent.o
-     34    0   288   322   142 getgrent.o
+     59    0     4    63    3f getgrent.o
-     38    0   288   326   146 getgrgid.o
+     63    0     4    67    43 getgrgid.o
-     38    0   288   326   146 getgrnam.o
+     63    0     4    67    43 getgrnam.o
-     34    0   288   322   142 getpwent.o
+     59    0     4    63    3f getpwent.o
-     38    0   288   326   146 getpwnam.o
+     63    0     4    67    43 getpwnam.o
-     38    0   288   326   146 getpwuid.o
+     63    0     4    67    43 getpwuid.o
-     34    0   320   354   162 getspent.o
+     59    0     4    63    3f getspent.o
-     38    0   320   358   166 getspnam.o
+     63    0     4    67    43 getspnam.o
-     38    0   320   358   166 sgetspent.o
+     40    0     4    44    2c sgetspent.o
-    458    0   172   630   276 getnetent.o
+    496    0     8   504   1f8 getnetent.o
-     45    0   480   525   20d gethostbyname.o
+     66    0     4    70    46 gethostbyname.o
-     53    0   492   545   221 gethostbyaddr.o
+     74    0     4    78    4e gethostbyaddr.o
-     49    0   492   541   21d gethostbyname2.o
+     70    0     4    74    4a gethostbyname2.o
-    189    0   168   357   165 gethostent.o
+    210    0    12   222    de gethostent.o
-    314    0   256   570   23a getpass.o
+    343    0     4   347   15b getpass.o
-   4097    0 70240 74337 12261 des.o
+   4391    0     8  4399  112f des.o
-   1921    0   160  2081   821 md5.o
+   1857    0     4  1861   745 md5.o

--
vda
diff -d -urpN uClibc.0/include/malloc.h uClibc.1/include/malloc.h
--- uClibc.0/include/malloc.h	2007-07-18 23:22:15.000000000 +0100
+++ uClibc.1/include/malloc.h	2007-07-20 22:47:09.000000000 +0100
@@ -183,6 +183,13 @@ extern int mallopt __MALLOC_P ((int __pa
 
 #endif /* __MALLOC_STANDARD__ */
 
+/* uClibc may use malloc internally in situations where user can not be
+ * notified about out-of-memory condition. In this situation uClibc will
+ * call __uc_malloc_failed if it is non-NULL, and retry allocation
+ * if it returns. If __uc_malloc_failed is NULL, uclubc will _exit(1).
+ * NB: do not use stdio in __uc_malloc_failed handler! */
+extern void *__uc_malloc(size_t size);
+extern void (*__uc_malloc_failed)(size_t size);
 
 #ifdef __cplusplus
 } /* end of extern "C" */
diff -d -urpN uClibc.0/libc/stdlib/Makefile.in uClibc.1/libc/stdlib/Makefile.in
--- uClibc.0/libc/stdlib/Makefile.in	2007-07-18 23:22:36.000000000 +0100
+++ uClibc.1/libc/stdlib/Makefile.in	2007-07-19 00:09:13.000000000 +0100
@@ -15,7 +15,7 @@ CSRC := \
 	getpt.c ptsname.c grantpt.c unlockpt.c drand48-iter.c jrand48.c \
 	jrand48_r.c lrand48.c lrand48_r.c mrand48.c mrand48_r.c nrand48.c \
 	nrand48_r.c rand_r.c srand48.c srand48_r.c seed48.c seed48_r.c \
-	valloc.c posix_memalign.c a64l.c l64a.c
+	valloc.c posix_memalign.c a64l.c l64a.c __uc_malloc.c
 ifeq ($(UCLIBC_HAS_ARC4RANDOM),y)
 CSRC += arc4random.c
 endif
diff -d -urpN uClibc.0/libc/stdlib/__uc_malloc.c uClibc.1/libc/stdlib/__uc_malloc.c
--- uClibc.0/libc/stdlib/__uc_malloc.c	1970-01-01 01:00:00.000000000 +0100
+++ uClibc.1/libc/stdlib/__uc_malloc.c	2007-07-19 00:07:04.000000000 +0100
@@ -0,0 +1,41 @@
+/* vi: set sw=4 ts=4: */
+/* uClibc internal malloc.
+   Copyright (C) 1991, 1992 Free Software Foundation, Inc.
+
+This library is free software; you can redistribute it and/or
+modify it under the terms of the GNU Library General Public License as
+published by the Free Software Foundation; either version 2 of the
+License, or (at your option) any later version.
+
+This library is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+Library General Public License for more details.
+
+You should have received a copy of the GNU Library General Public
+License along with this library; see the file COPYING.LIB.  If
+not, write to the Free Software Foundation, Inc., 675 Mass Ave,
+Cambridge, MA 02139, USA.
+
+   The author may be reached (Email) at the address mike@@ai.mit.edu,
+   or (US mail) as Mike Haertel c/o Free Software Foundation.  */
+
+#include <stdlib.h>
+#include <unistd.h>
+#include <malloc.h>
+
+void (*__uc_malloc_failed)(size_t size);
+
+void *__uc_malloc(size_t size)
+{
+	void *p;
+
+	while (1) {
+		p = malloc(size);
+		if (!size || p)
+			return p;
+		if (!__uc_malloc_failed)
+			_exit(1);
+		__uc_malloc_failed(size);
+	}
+}
diff -d -urpN uClibc.1/libcrypt/des.c uClibc.2/libcrypt/des.c
--- uClibc.1/libcrypt/des.c	2007-07-18 23:12:42.000000000 +0100
+++ uClibc.2/libcrypt/des.c	2007-07-21 16:06:17.000000000 +0100
@@ -64,32 +64,67 @@
 #include <pwd.h>
 #include <string.h>
 #include <crypt.h>
+#include <stdlib.h>
+#include <malloc.h>
 #include "libcrypt.h"
 
-/* Re-entrantify me -- all this junk needs to be in 
- * struct crypt_data to make this really reentrant... */
-static u_char	inv_key_perm[64];
-static u_char	inv_comp_perm[56];
-static u_char	un_pbox[32];
-static u_int32_t en_keysl[16], en_keysr[16];
-static u_int32_t de_keysl[16], de_keysr[16];
-static u_int32_t ip_maskl[8][256], ip_maskr[8][256];
-static u_int32_t fp_maskl[8][256], fp_maskr[8][256];
-static u_int32_t key_perm_maskl[8][128], key_perm_maskr[8][128];
-static u_int32_t comp_maskl[8][128], comp_maskr[8][128];
-static u_int32_t saltbits;
-static u_int32_t old_salt;
-static u_int32_t old_rawkey0, old_rawkey1;
+/* We allocate memory for tables on first use, instead of using
+ * static buffers - ~70k of statics is not NOMMU-friendly. */
 
+struct crypt_data {
+	u_int32_t saltbits; // referenced 5 times
+	u_int32_t old_salt; // 3
+	u_int32_t old_rawkey0, old_rawkey1; // 3,3
+	u_char	un_pbox[32]; // 2
+	u_char	inv_comp_perm[56]; // 3
+	u_char	inv_key_perm[64]; // 3
+	char	des_initialised; // 2
+	char	__des_crypt_out[21]; /* private buffer for __des_crypt() */
+	u_int32_t en_keysl[16], en_keysr[16]; // 2,2
+	u_int32_t de_keysl[16], de_keysr[16]; // 2,2
+	u_int32_t ip_maskl[8][256], ip_maskr[8][256]; // 9,9
+	u_int32_t fp_maskl[8][256], fp_maskr[8][256]; // 9,9
+	u_int32_t key_perm_maskl[8][128], key_perm_maskr[8][128]; // 9,9
+	u_int32_t comp_maskl[8][128], comp_maskr[8][128]; // 9,9
+};
+static struct crypt_data *__uc_des_data;
+#define D (*__uc_des_data)
+#define saltbits        (D.saltbits       )
+#define old_salt        (D.old_salt       )
+#define old_rawkey0     (D.old_rawkey0    )
+#define old_rawkey1     (D.old_rawkey1    )
+#define un_pbox         (D.un_pbox        )
+#define inv_comp_perm   (D.inv_comp_perm  )
+#define inv_key_perm    (D.inv_key_perm   )
+#define des_initialised (D.des_initialised)
+#define __des_crypt_out (D.__des_crypt_out)
+#define en_keysl        (D.en_keysl       )
+#define en_keysr        (D.en_keysr       )
+#define de_keysl        (D.de_keysl       )
+#define de_keysr        (D.de_keysr       )
+#define ip_maskl        (D.ip_maskl       )
+#define ip_maskr        (D.ip_maskr       )
+#define fp_maskl        (D.fp_maskl       )
+#define fp_maskr        (D.fp_maskr       )
+#define key_perm_maskl  (D.key_perm_maskl )
+#define key_perm_maskr  (D.key_perm_maskr )
+#define comp_maskl      (D.comp_maskl     )
+#define comp_maskr      (D.comp_maskr     )
 
 /* Static stuff that stays resident and doesn't change after 
  * being initialized, and therefore doesn't need to be made 
  * reentrant. */
-static u_char	init_perm[64], final_perm[64];
-static u_char	m_sbox[4][4096];
-static u_int32_t psbox[4][256];
-
-
+struct const_crypt_data {
+	u_char	init_perm[64], final_perm[64]; // 2,2
+	u_char	m_sbox[4][4096]; // 5
+	u_int32_t psbox[4][256]; // 5
+};
+static struct const_crypt_data *__uc_des_C_ptr;
+#define C (*__uc_des_C_ptr)
+#define init_perm  (C.init_perm )
+#define final_perm (C.final_perm)
+#define m_sbox     (C.m_sbox    )
+#define psbox      (C.psbox     )
 
 
 /* A pile of data */
@@ -216,16 +251,19 @@ ascii_to_bin(char ch)
 static void
 des_init(void)
 {
-	static int des_initialised = 0;
-
 	int	i, j, b, k, inbit, obit;
 	u_int32_t	*p, *il, *ir, *fl, *fr;
 	const u_int32_t *bits28, *bits24;
 	u_char	u_sbox[8][64];
 
-	if (des_initialised==1)
+	if (des_initialised)
 		return;
 
+	if (!__uc_des_C_ptr) {
+		/* No need to zero it out, it is fully initialized below */
+		__uc_des_C_ptr = __uc_malloc(sizeof(C));
+	}
+
 	old_rawkey0 = old_rawkey1 = 0L;
 	saltbits = 0L;
 	old_salt = 0L;
@@ -459,7 +497,8 @@ do_des(	u_int32_t l_in, u_int32_t r_in, 
 	 *	l_in, r_in, l_out, and r_out are in pseudo-"big-endian" format.
 	 */
 	u_int32_t	l, r, *kl, *kr, *kl1, *kr1;
-	u_int32_t	f, r48l, r48r;
+	u_int32_t	f = f; /* silence gcc */
+	u_int32_t	r48l, r48r;
 	int		round;
 
 	if (count == 0) {
@@ -605,6 +644,9 @@ setkey(const char *key)
 	u_int32_t	packed_keys[2];
 	u_char	*p;
 
+	if (!__uc_des_data)
+		__uc_des_data = memset(__uc_malloc(sizeof(D)), 0, sizeof(D));
+
 	p = (u_char *) packed_keys;
 
 	for (i = 0; i < 8; i++) {
@@ -624,6 +666,9 @@ encrypt(char *block, int flag)
 	u_char	*p;
 	int	i, j;
 
+        /* if user didn't call setkey() before and __uc_des_data
+         * is NULL, it's user's own fault. */
+
 	des_init();
 
 	setup_salt(0L);
@@ -640,11 +685,20 @@ encrypt(char *block, int flag)
 			block[(i << 5) | j] = (io[i] & bits32[j]) ? 1 : 0;
 }
 
+
 char *__des_crypt(const unsigned char *key, const unsigned char *setting)
 {
 	u_int32_t	count, salt, l, r0, r1, keybuf[2];
 	u_char		*p, *q;
-	static char	output[21];
+
+/* Used to have static char output[21] here, but since we already
+ * allocate ~70k for des tables, we can carve out 21 bytes
+ * from that memory instead */
+#define output __des_crypt_out
+
+	if (!__uc_des_data) {
+		__uc_des_data = memset(__uc_malloc(sizeof(D)), 0, sizeof(D));
+	}
 
 	des_init();
 
diff -d -urpN uClibc.2/libc/inet/resolv.c uClibc.3/libc/inet/resolv.c
--- uClibc.2/libc/inet/resolv.c	2007-07-18 23:22:33.000000000 +0100
+++ uClibc.3/libc/inet/resolv.c	2007-07-20 23:26:43.000000000 +0100
@@ -146,6 +146,7 @@
 #include <netinet/in.h>
 #include <arpa/inet.h>
 #include <stdlib.h>
+#include <malloc.h>
 #include <unistd.h>
 #include <resolv.h>
 #include <netdb.h>
@@ -1122,13 +1123,17 @@ void attribute_hidden __close_nameserver
 
 struct hostent *gethostbyname(const char *name)
 {
-	static struct hostent h;
-	static char buf[sizeof(struct in_addr) +
+	static struct {
+		struct hostent h;
+		char buf[sizeof(struct in_addr) +
 					sizeof(struct in_addr *)*2 +
 					sizeof(char *)*(ALIAS_DIM) + 384/*namebuffer*/ + 32/* margin */];
+	} *sp;
 	struct hostent *hp;
 
-	gethostbyname_r(name, &h, buf, sizeof(buf), &hp, &h_errno);
+	free(sp);
+	sp = __uc_malloc(sizeof(*sp));
+	gethostbyname_r(name, &sp->h, sp->buf, sizeof(sp->buf), &hp, &h_errno);
 
 	return hp;
 }
@@ -1142,13 +1147,17 @@ struct hostent *gethostbyname2(const cha
 #ifndef __UCLIBC_HAS_IPV6__
 	return family == AF_INET ? gethostbyname(name) : (struct hostent*)0;
 #else /* __UCLIBC_HAS_IPV6__ */
-	static struct hostent h;
-	static char buf[sizeof(struct in6_addr) +
+	static struct {
+		struct hostent h;
+		char buf[sizeof(struct in6_addr) +
 					sizeof(struct in6_addr *)*2 +
 					sizeof(char *)*(ALIAS_DIM) + 384/*namebuffer*/ + 32/* margin */];
+	} *sp;
 	struct hostent *hp;
 
-	gethostbyname2_r(name, family, &h, buf, sizeof(buf), &hp, &h_errno);
+	free(sp);
+	sp = __uc_malloc(sizeof(*sp));
+	gethostbyname2_r(name, family, &sp->h, sp->buf, sizeof(sp->buf), &hp, &h_errno);
 
 	return hp;
 #endif /* __UCLIBC_HAS_IPV6__ */
@@ -1496,17 +1505,21 @@ libc_hidden_def(res_querydomain)
 #ifdef L_gethostbyaddr
 struct hostent *gethostbyaddr (const void *addr, socklen_t len, int type)
 {
-	static struct hostent h;
-	static char buf[
+	static struct {
+		struct hostent h;
+		char buf[
 #ifndef __UCLIBC_HAS_IPV6__
 					sizeof(struct in_addr) + sizeof(struct in_addr *)*2 +
 #else
 					sizeof(struct in6_addr) + sizeof(struct in6_addr *)*2 +
 #endif /* __UCLIBC_HAS_IPV6__ */
 					sizeof(char *)*(ALIAS_DIM) + 384/*namebuffer*/ + 32/* margin */];
+	} *sp;
 	struct hostent *hp;
 
-	gethostbyaddr_r(addr, len, type, &h, buf, sizeof(buf), &hp, &h_errno);
+	free(sp);
+	sp = __uc_malloc(sizeof(*sp));
+	gethostbyaddr_r(addr, len, type, &sp->h, sp->buf, sizeof(sp->buf), &hp, &h_errno);
 
 	return hp;
 }
@@ -1725,8 +1738,9 @@ libc_hidden_def(gethostent_r)
 
 struct hostent *gethostent (void)
 {
-    static struct hostent h;
-    static char buf[
+    static struct {
+	struct hostent h;
+	char buf[
 #ifndef __UCLIBC_HAS_IPV6__
 					sizeof(struct in_addr) + sizeof(struct in_addr *)*2 +
 #else
@@ -1734,10 +1748,13 @@ struct hostent *gethostent (void)
 #endif /* __UCLIBC_HAS_IPV6__ */
 					sizeof(char *)*(ALIAS_DIM) +
 					80/*namebuffer*/ + 2/* margin */];
+    } *sp;
     struct hostent *host;
 
+    free(sp);
+    sp = __uc_malloc(sizeof(*sp));
     __UCLIBC_MUTEX_LOCK(mylock);
-    gethostent_r(&h, buf, sizeof(buf), &host, &h_errno);
+    gethostent_r(&sp->h, sp->buf, sizeof(sp->buf), &host, &h_errno);
     __UCLIBC_MUTEX_UNLOCK(mylock);
     return(host);
 }
diff -d -urpN uClibc.2/libcrypt/des.c uClibc.3/libcrypt/des.c
--- uClibc.2/libcrypt/des.c	2007-07-21 16:06:17.000000000 +0100
+++ uClibc.3/libcrypt/des.c	2007-07-21 16:13:05.000000000 +0100
@@ -697,6 +697,7 @@ char *__des_crypt(const unsigned char *k
 #define output __des_crypt_out
 
 	if (!__uc_des_data) {
+		/* If malloc returns NULL, we just segfault. Other ideas? */
 		__uc_des_data = memset(__uc_malloc(sizeof(D)), 0, sizeof(D));
 	}
 
diff -d -urpN uClibc.3/libc/pwd_grp/pwd_grp.c uClibc.4/libc/pwd_grp/pwd_grp.c
--- uClibc.3/libc/pwd_grp/pwd_grp.c	2007-07-18 23:22:36.000000000 +0100
+++ uClibc.4/libc/pwd_grp/pwd_grp.c	2007-07-20 23:36:46.000000000 +0100
@@ -23,6 +23,7 @@
 #include <stdio.h>
 #include <stdlib.h>
 #include <stdint.h>
+#include <malloc.h>
 #include <string.h>
 #include <stddef.h>
 #include <errno.h>
@@ -157,11 +158,15 @@ libc_hidden_proto(fgetpwent_r)
 
 struct passwd *fgetpwent(FILE *stream)
 {
-	static char buffer[__UCLIBC_PWD_BUFFER_SIZE__];
-	static struct passwd resultbuf;
+	static struct {
+		char buffer[__UCLIBC_PWD_BUFFER_SIZE__];
+		struct passwd resultbuf;
+	} *sp;
 	struct passwd *result;
 
-	fgetpwent_r(stream, &resultbuf, buffer, sizeof(buffer), &result);
+	free(sp);
+	sp = __uc_malloc(sizeof(*sp));
+	fgetpwent_r(stream, &sp->resultbuf, sp->buffer, sizeof(sp->buffer), &result);
 	return result;
 }
 #endif
@@ -175,11 +180,15 @@ libc_hidden_proto(fgetgrent_r)
 
 struct group *fgetgrent(FILE *stream)
 {
-	static char buffer[__UCLIBC_GRP_BUFFER_SIZE__];
-	static struct group resultbuf;
+	static struct {
+		char buffer[__UCLIBC_GRP_BUFFER_SIZE__];
+		struct group resultbuf;
+	} *sp;
 	struct group *result;
 
-	fgetgrent_r(stream, &resultbuf, buffer, sizeof(buffer), &result);
+	free(sp);
+	sp = __uc_malloc(sizeof(*sp));
+	fgetgrent_r(stream, &sp->resultbuf, sp->buffer, sizeof(sp->buffer), &result);
 	return result;
 }
 #endif
@@ -192,11 +201,15 @@ libc_hidden_proto(fgetspent_r)
 
 struct spwd *fgetspent(FILE *stream)
 {
-	static char buffer[__UCLIBC_PWD_BUFFER_SIZE__];
-	static struct spwd resultbuf;
+	static struct {
+		char buffer[__UCLIBC_PWD_BUFFER_SIZE__];
+		struct spwd resultbuf;
+	} *sp;
 	struct spwd *result;
 
-	fgetspent_r(stream, &resultbuf, buffer, sizeof(buffer), &result);
+	free(sp);
+	sp = __uc_malloc(sizeof(*sp));
+	fgetspent_r(stream, &sp->resultbuf, sp->buffer, sizeof(sp->buffer), &result);
 	return result;
 }
 
@@ -298,11 +311,15 @@ libc_hidden_proto(getpwuid_r)
 
 struct passwd *getpwuid(uid_t uid)
 {
-	static char buffer[__UCLIBC_PWD_BUFFER_SIZE__];
-	static struct passwd resultbuf;
+	static struct {
+		char buffer[__UCLIBC_PWD_BUFFER_SIZE__];
+		struct passwd resultbuf;
+	} *sp;
 	struct passwd *result;
 
-	getpwuid_r(uid, &resultbuf, buffer, sizeof(buffer), &result);
+	free(sp);
+	sp = __uc_malloc(sizeof(*sp));
+	getpwuid_r(uid, &sp->resultbuf, sp->buffer, sizeof(sp->buffer), &result);
 	return result;
 }
 
@@ -314,11 +331,15 @@ libc_hidden_proto(getgrgid_r)
 
 struct group *getgrgid(gid_t gid)
 {
-	static char buffer[__UCLIBC_GRP_BUFFER_SIZE__];
-	static struct group resultbuf;
+	static struct {
+		char buffer[__UCLIBC_GRP_BUFFER_SIZE__];
+		struct group resultbuf;
+	} *sp;
 	struct group *result;
 
-	getgrgid_r(gid, &resultbuf, buffer, sizeof(buffer), &result);
+	free(sp);
+	sp = __uc_malloc(sizeof(*sp));
+	getgrgid_r(gid, &sp->resultbuf, sp->buffer, sizeof(sp->buffer), &result);
 	return result;
 }
 
@@ -361,11 +382,15 @@ libc_hidden_proto(getspuid_r)
 
 struct spwd *getspuid(uid_t uid)
 {
-	static char buffer[__UCLIBC_PWD_BUFFER_SIZE__];
-	static struct spwd resultbuf;
+	static struct {
+		char buffer[__UCLIBC_PWD_BUFFER_SIZE__];
+		struct spwd resultbuf;
+	} *sp;
 	struct spwd *result;
 
-	getspuid_r(uid, &resultbuf, buffer, sizeof(buffer), &result);
+	free(sp);
+	sp = __uc_malloc(sizeof(*sp));
+	getspuid_r(uid, &sp->resultbuf, sp->buffer, sizeof(sp->buffer), &result);
 	return result;
 }
 
@@ -377,11 +402,15 @@ libc_hidden_proto(getpwnam_r)
 
 struct passwd *getpwnam(const char *name)
 {
-	static char buffer[__UCLIBC_PWD_BUFFER_SIZE__];
-	static struct passwd resultbuf;
+	static struct {
+		char buffer[__UCLIBC_PWD_BUFFER_SIZE__];
+		struct passwd resultbuf;
+	} *sp;
 	struct passwd *result;
 
-	getpwnam_r(name, &resultbuf, buffer, sizeof(buffer), &result);
+	free(sp);
+	sp = __uc_malloc(sizeof(*sp));
+	getpwnam_r(name, &sp->resultbuf, sp->buffer, sizeof(sp->buffer), &result);
 	return result;
 }
 
@@ -393,11 +422,15 @@ libc_hidden_proto(getgrnam_r)
 
 struct group *getgrnam(const char *name)
 {
-	static char buffer[__UCLIBC_GRP_BUFFER_SIZE__];
-	static struct group resultbuf;
+	static struct {
+		char buffer[__UCLIBC_GRP_BUFFER_SIZE__];
+		struct group resultbuf;
+	} *sp;
 	struct group *result;
 
-	getgrnam_r(name, &resultbuf, buffer, sizeof(buffer), &result);
+	free(sp);
+	sp = __uc_malloc(sizeof(*sp));
+	getgrnam_r(name, &sp->resultbuf, sp->buffer, sizeof(sp->buffer), &result);
 	return result;
 }
 
@@ -409,11 +442,15 @@ libc_hidden_proto(getspnam_r)
 
 struct spwd *getspnam(const char *name)
 {
-	static char buffer[__UCLIBC_PWD_BUFFER_SIZE__];
-	static struct spwd resultbuf;
+	static struct {
+		char buffer[__UCLIBC_PWD_BUFFER_SIZE__];
+		struct spwd resultbuf;
+	} *sp;
 	struct spwd *result;
 
-	getspnam_r(name, &resultbuf, buffer, sizeof(buffer), &result);
+	free(sp);
+	sp = __uc_malloc(sizeof(*sp));
+	getspnam_r(name, &sp->resultbuf, sp->buffer, sizeof(sp->buffer), &result);
 	return result;
 }
 
@@ -626,11 +663,15 @@ libc_hidden_proto(getpwent_r)
 
 struct passwd *getpwent(void)
 {
-	static char line_buff[__UCLIBC_PWD_BUFFER_SIZE__];
-	static struct passwd pwd;
+	static struct {
+		char line_buff[__UCLIBC_PWD_BUFFER_SIZE__];
+		struct passwd pwd;
+	} *sp;
 	struct passwd *result;
 
-	getpwent_r(&pwd, line_buff, sizeof(line_buff), &result);
+	free(sp);
+	sp = __uc_malloc(sizeof(*sp));
+	getpwent_r(&sp->pwd, sp->line_buff, sizeof(sp->line_buff), &result);
 	return result;
 }
 
@@ -642,11 +683,15 @@ libc_hidden_proto(getgrent_r)
 
 struct group *getgrent(void)
 {
-	static char line_buff[__UCLIBC_GRP_BUFFER_SIZE__];
-	static struct group gr;
+	static struct {
+		char line_buff[__UCLIBC_GRP_BUFFER_SIZE__];
+		struct group gr;
+	} *sp;
 	struct group *result;
 
-	getgrent_r(&gr, line_buff, sizeof(line_buff), &result);
+	free(sp);
+	sp = __uc_malloc(sizeof(*sp));
+	getgrent_r(&sp->gr, sp->line_buff, sizeof(sp->line_buff), &result);
 	return result;
 }
 
@@ -658,11 +703,15 @@ libc_hidden_proto(getspent_r)
 
 struct spwd *getspent(void)
 {
-	static char line_buff[__UCLIBC_PWD_BUFFER_SIZE__];
-	static struct spwd spwd;
+	static struct {
+		char line_buff[__UCLIBC_PWD_BUFFER_SIZE__];
+		struct spwd spwd;
+	} *sp;
 	struct spwd *result;
 
-	getspent_r(&spwd, line_buff, sizeof(line_buff), &result);
+	free(sp);
+	sp = __uc_malloc(sizeof(*sp));
+	getspent_r(&sp->spwd, sp->line_buff, sizeof(sp->line_buff), &result);
 	return result;
 }
 
@@ -674,11 +723,13 @@ libc_hidden_proto(sgetspent_r)
 
 struct spwd *sgetspent(const char *string)
 {
-	static char line_buff[__UCLIBC_PWD_BUFFER_SIZE__];
-	static struct spwd spwd;
+	static struct {
+		char line_buff[__UCLIBC_PWD_BUFFER_SIZE__];
+		struct spwd spwd;
+	} *sp;
 	struct spwd *result;
 
-	sgetspent_r(string, &spwd, line_buff, sizeof(line_buff), &result);
+	sgetspent_r(string, &sp->spwd, sp->line_buff, sizeof(sp->line_buff), &result);
 	return result;
 }
 
diff -d -urpN uClibc.4/libc/misc/utmp/utent.c uClibc.5/libc/misc/utmp/utent.c
--- uClibc.4/libc/misc/utmp/utent.c	2007-07-18 23:23:05.000000000 +0100
+++ uClibc.5/libc/misc/utmp/utent.c	2007-07-20 23:54:52.000000000 +0100
@@ -14,6 +14,7 @@
 #include <stdio.h>
 #include <stdlib.h>
 #include <unistd.h>
+#include <malloc.h>
 #include <fcntl.h>
 #include <paths.h>
 #include <errno.h>
@@ -36,9 +37,10 @@ __UCLIBC_MUTEX_STATIC(utmplock, PTHREAD_
 
 
 /* Some global crap */
-static int static_fd = -1;
-static struct utmp static_utmp;
 static const char default_file_name[] = _PATH_UTMP;
+
+static int static_fd = -1;
+static struct utmp *static_utmp;
 static const char *static_ut_name = (const char *) default_file_name;
 
 /* This function must be called with the LOCK held */
@@ -89,9 +91,11 @@ static struct utmp *__getutent(int utmp_
 	return NULL;
     }
 
-    if (read(utmp_fd, (char *) &static_utmp, sizeof(struct utmp)) == sizeof(struct utmp))
+    free(static_utmp);
+    static_utmp = __uc_malloc(sizeof(*static_utmp));
+    if (read(utmp_fd, (char *) static_utmp, sizeof(*static_utmp)) == sizeof(*static_utmp))
     {
-	ret = &static_utmp;
+	ret = static_utmp;
     }
 
     return ret;
diff -d -urpN uClibc.4/libc/unistd/getpass.c uClibc.5/libc/unistd/getpass.c
--- uClibc.4/libc/unistd/getpass.c	2007-07-18 23:22:44.000000000 +0100
+++ uClibc.5/libc/unistd/getpass.c	2007-07-20 23:53:46.000000000 +0100
@@ -20,7 +20,7 @@
 #include <string.h>
 #include <termios.h>
 #include <unistd.h>
-#include <string.h>
+#include <malloc.h>
 
 #if defined __USE_BSD || (defined __USE_XOPEN && !defined __USE_XOPEN2K)
 
@@ -52,12 +52,16 @@ char *
 getpass (prompt)
      const char *prompt;
 {
+  static char *buf;
+
   FILE *in, *out;
   struct termios s, t;
   int tty_changed;
-  static char buf[PWD_BUFFER_SIZE];
   int nread;
 
+  free(buf);
+  buf = __uc_malloc(PWD_BUFFER_SIZE);
+
   /* Try to write to and read from the terminal if we can.
      If we can't open the terminal, use stderr and stdin.  */
 
diff -d -urpN uClibc.5/libc/inet/getnetent.c uClibc.6/libc/inet/getnetent.c
--- uClibc.5/libc/inet/getnetent.c	2007-07-18 23:22:33.000000000 +0100
+++ uClibc.6/libc/inet/getnetent.c	2007-07-21 00:26:12.000000000 +0100
@@ -19,6 +19,7 @@
 #include <features.h>
 #include <stdio.h>
 #include <stdlib.h>
+#include <malloc.h>
 #include <netdb.h>
 #include <arpa/inet.h>
 
@@ -32,14 +33,9 @@ libc_hidden_proto(abort)
 #include <bits/uClibc_mutex.h>
 __UCLIBC_MUTEX_STATIC(mylock, PTHREAD_MUTEX_INITIALIZER);
 
-
-
-#define	MAXALIASES	35
 static const char NETDB[] = _PATH_NETWORKS;
+
 static FILE *netf = NULL;
-static char *line = NULL;
-static struct netent net;
-static char *net_aliases[MAXALIASES];
 
 int _net_stayopen attribute_hidden;
 
@@ -83,6 +79,22 @@ static char * any(register char *cp, cha
     return ((char *)0);
 }
 
+#define	MAXALIASES	35
+static struct {
+	char *line;
+	struct netent net;
+	char *net_aliases[MAXALIASES];
+} *sp;
+#define line        (sp->line)
+#define net         (sp->net)
+#define net_aliases (sp->net_aliases)
+#define INIT_SP() { \
+    if (!sp) { \
+	sp = __uc_malloc(sizeof(*sp)); \
+	line = NULL; \
+    } \
+}
+
 libc_hidden_proto(getnetent)
 struct netent *getnetent(void)
 {
@@ -90,6 +102,8 @@ struct netent *getnetent(void)
     register char *cp, **q;
     struct netent *rv = NULL;
 
+    INIT_SP();
+
     __UCLIBC_MUTEX_LOCK(mylock);
     if (netf == NULL && (netf = fopen(NETDB, "r" )) == NULL) {
 	goto DONE;
diff -d -urpN uClibc.5/libcrypt/md5.c uClibc.6/libcrypt/md5.c
--- uClibc.5/libcrypt/md5.c	2007-07-18 23:22:27.000000000 +0100
+++ uClibc.6/libcrypt/md5.c	2007-07-21 00:20:22.000000000 +0100
@@ -76,6 +76,7 @@
 #include <sys/types.h>
 #include <string.h>
 #include <unistd.h>
+#include <malloc.h>
 #include <stdio.h>
 #include <crypt.h>
 #include <sys/cdefs.h>
@@ -95,7 +96,10 @@ static void   __md5_Final (unsigned char
 static void __md5_Transform __P((u_int32_t [4], const unsigned char [64]));
 
 
-static const unsigned char __md5__magic[] = "$1$";	/* This string is magic for this algorithm.  Having 
+#define MD5_MAGIC_STR "$1$"
+#define MD5_MAGIC_LEN (sizeof(MD5_MAGIC_STR) - 1)
+static const unsigned char __md5__magic[] = MD5_MAGIC_STR;
+						/* This string is magic for this algorithm.  Having 
 						   it this way, we can get better later on */
 static const unsigned char __md5_itoa64[] =		/* 0 ... 63 => ascii - 64 */
 	"./0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
@@ -534,21 +538,24 @@ static void __md5_to64( char *s, unsigne
 char *__md5_crypt(const unsigned char *pw, const unsigned char *salt)
 {
 	/* Static stuff */
-	static const unsigned char *sp, *ep;
-	static char passwd[120], *p;
+	static char *passwd;
 
+	const unsigned char *sp, *ep;
+	char *p;
 	unsigned char	final[17];	/* final[16] exists only to aid in looping */
-	int sl,pl,i,__md5__magic_len,pw_len;
+	int sl,pl,i,pw_len;
 	struct MD5Context ctx,ctx1;
 	unsigned long l;
 
+	if (!passwd)
+		passwd = __uc_malloc(120);
+
 	/* Refine the Salt first */
 	sp = salt;
 
 	/* If it starts with the magic string, then skip that */
-	__md5__magic_len = strlen(__md5__magic);
-	if(!strncmp(sp,__md5__magic,__md5__magic_len))
-		sp += __md5__magic_len;
+	if(!strncmp(sp,__md5__magic,MD5_MAGIC_LEN))
+		sp += MD5_MAGIC_LEN;
 
 	/* It stops at the first '$', max 8 chars */
 	for(ep=sp;*ep && *ep != '$' && ep < (sp+8);ep++)
@@ -564,7 +571,7 @@ char *__md5_crypt(const unsigned char *p
 	__md5_Update(&ctx,pw,pw_len);
 
 	/* Then our magic string */
-	__md5_Update(&ctx,__md5__magic,__md5__magic_len);
+	__md5_Update(&ctx,__md5__magic,MD5_MAGIC_LEN);
 
 	/* Then the raw salt */
 	__md5_Update(&ctx,sp,sl);
_______________________________________________
uClibc mailing list
[email protected]
http://busybox.net/cgi-bin/mailman/listinfo/uclibc

Reply via email to