Annotation of src/usr.bin/ssh/tildexpand.c, Revision 1.11
1.1 deraadt 1: /*
1.4 deraadt 2: * Author: Tatu Ylonen <ylo@cs.hut.fi>
3: * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland
4: * All rights reserved
1.8 deraadt 5: *
6: * As far as I am concerned, the code I have written for this software
7: * can be used freely for any purpose. Any derived versions of this
8: * software must be clearly marked as such, and if the derived work is
9: * incompatible with the protocol description in the RFC file, it must be
10: * called by a name other than "ssh" or "Secure Shell".
1.4 deraadt 11: */
1.1 deraadt 12:
13: #include "includes.h"
1.11 ! itojun 14: RCSID("$OpenBSD: tildexpand.c,v 1.10 2001/01/21 19:06:01 markus Exp $");
1.1 deraadt 15:
16: #include "xmalloc.h"
1.10 markus 17: #include "log.h"
1.11 ! itojun 18: #include "tildexpand.h"
1.1 deraadt 19:
1.4 deraadt 20: /*
21: * Expands tildes in the file name. Returns data allocated by xmalloc.
22: * Warning: this calls getpw*.
23: */
1.3 markus 24: char *
25: tilde_expand_filename(const char *filename, uid_t my_uid)
1.1 deraadt 26: {
1.3 markus 27: const char *cp;
1.9 markus 28: u_int userlen;
1.3 markus 29: char *expanded;
30: struct passwd *pw;
31: char user[100];
1.6 deraadt 32: int len;
1.3 markus 33:
34: /* Return immediately if no tilde. */
35: if (filename[0] != '~')
36: return xstrdup(filename);
37:
38: /* Skip the tilde. */
39: filename++;
40:
41: /* Find where the username ends. */
42: cp = strchr(filename, '/');
43: if (cp)
1.4 deraadt 44: userlen = cp - filename; /* Something after username. */
1.3 markus 45: else
1.4 deraadt 46: userlen = strlen(filename); /* Nothing after username. */
1.3 markus 47: if (userlen == 0)
1.5 markus 48: pw = getpwuid(my_uid); /* Own home directory. */
1.3 markus 49: else {
50: /* Tilde refers to someone elses home directory. */
51: if (userlen > sizeof(user) - 1)
52: fatal("User name after tilde too long.");
53: memcpy(user, filename, userlen);
54: user[userlen] = 0;
55: pw = getpwnam(user);
56: }
57: if (!pw)
58: fatal("Unknown user %100s.", user);
59:
60: /* If referring to someones home directory, return it now. */
1.5 markus 61: if (!cp) {
62: /* Only home directory specified */
1.3 markus 63: return xstrdup(pw->pw_dir);
64: }
65: /* Build a path combining the specified directory and path. */
1.6 deraadt 66: len = strlen(pw->pw_dir) + strlen(cp + 1) + 2;
67: if (len > MAXPATHLEN)
68: fatal("Home directory too long (%d > %d", len-1, MAXPATHLEN-1);
69: expanded = xmalloc(len);
70: snprintf(expanded, len, "%s/%s", pw->pw_dir, cp + 1);
1.3 markus 71: return expanded;
1.1 deraadt 72: }