Skip to content

Commit d7f32b7

Browse files
lib/agetpass.*: Use alloca(3) to minimize visibility of passwords
The stack should have enough space for PASS_MAX+2 allocations. Signed-off-by: Alejandro Colomar <[email protected]>
1 parent 0866b23 commit d7f32b7

File tree

2 files changed

+14
-16
lines changed

2 files changed

+14
-16
lines changed

lib/agetpass.c

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,4 +8,5 @@
88

99

1010
extern inline void erase_pass(char *pass);
11-
extern inline char *agetpass_internal(const char *prompt, int flags);
11+
extern inline char *getpass_(char pass[SIZE_MAX + 2], const char *prompt,
12+
int flags);

lib/agetpass.h

Lines changed: 12 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -8,32 +8,33 @@
88

99
#include <config.h>
1010

11+
#include <alloca.h>
12+
#include <errno.h>
1113
#include <limits.h>
1214
#include <readpassphrase.h>
15+
#include <stddef.h>
1316
#include <stdlib.h>
1417
#include <string.h>
1518

1619
#include "alloc/malloc.h"
17-
18-
#if WITH_LIBBSD == 0
19-
#include "freezero.h"
20-
#endif /* WITH_LIBBSD */
20+
#include "memzero.h"
2121

2222

2323
// Similar to getpass(3), but free of its problems.
24-
#define agetpass(prompt) agetpass_internal(prompt, RPP_REQUIRE_TTY)
25-
#define agetpass_stdin() agetpass_internal(NULL, RPP_STDIN)
24+
#define agetpass(prompt) agetpass_(prompt, RPP_REQUIRE_TTY)
25+
#define agetpass_stdin() agetpass_(NULL, RPP_STDIN)
26+
27+
#define agetpass_(...) getpass_(alloca(PASS_MAX + 2), __VA_ARGS__)
2628

2729

2830
inline void erase_pass(char *pass);
2931
ATTR_MALLOC(erase_pass)
30-
inline char *agetpass_internal(const char *prompt, int flags);
32+
inline char *getpass_(char pass[PASS_MAX + 2], const char *prompt, int flags);
3133

3234

3335
inline char *
34-
agetpass_internal(const char *prompt, int flags)
36+
getpass_(char pass[PASS_MAX + 2], const char *prompt, int flags)
3537
{
36-
char *pass;
3738
size_t len;
3839

3940
/*
@@ -44,10 +45,6 @@ agetpass_internal(const char *prompt, int flags)
4445
* Let's add one more byte, and if the password uses it, it
4546
* means the introduced password was longer than PASS_MAX.
4647
*/
47-
pass = MALLOC(PASS_MAX + 2, char);
48-
if (pass == NULL)
49-
return NULL;
50-
5148
if (readpassphrase(prompt, pass, PASS_MAX + 2, flags) == NULL)
5249
goto fail;
5350

@@ -60,15 +57,15 @@ agetpass_internal(const char *prompt, int flags)
6057
return pass;
6158

6259
fail:
63-
freezero(pass, PASS_MAX + 2);
60+
memzero(pass, PASS_MAX + 2);
6461
return NULL;
6562
}
6663

6764

6865
inline void
6966
erase_pass(char *pass)
7067
{
71-
freezero(pass, PASS_MAX + 2);
68+
memzero(pass, PASS_MAX + 2);
7269
}
7370

7471

0 commit comments

Comments
 (0)