1 // Functions which allow the client to remember usernames and passwords for
4 // Copyright (c) 1987-2023 by the citadel.org team
6 // This program is open source software. Use, duplication, and/or
7 // disclosure are subject to the GNU General Purpose License version 3.
9 #include "textclient.h"
11 #define PWFILENAME "%s/.citadel.passwords"
13 void determine_pwfilename(char *pwfile, size_t n) {
16 p = getpwuid(getuid());
19 snprintf(pwfile, n, PWFILENAME, p->pw_dir);
23 // Check the password file for a host/port match; if found, stuff the user
24 // name and password into the user/pass buffers
25 void get_stored_password(char *host, char *port, char *username, char *password) {
27 char pwfile[PATH_MAX];
31 char hostbuf[256], portbuf[256], ubuf[256], pbuf[256];
36 determine_pwfilename(pwfile, sizeof pwfile);
37 if (IsEmptyStr(pwfile))
40 fp = fopen(pwfile, "r");
44 while (fgets(buf64, sizeof buf64, fp) != NULL) {
45 CtdlDecodeBase64(buf, buf64, sizeof(buf64));
46 extract_token(hostbuf, buf, 0, '|', sizeof hostbuf);
47 extract_token(portbuf, buf, 1, '|', sizeof portbuf);
48 extract_token(ubuf, buf, 2, '|', sizeof ubuf);
49 extract_token(pbuf, buf, 3, '|', sizeof pbuf);
51 if (!strcasecmp(hostbuf, host)) {
52 if (!strcasecmp(portbuf, port)) {
53 strcpy(username, ubuf);
54 strcpy(password, pbuf);
62 // Set (or clear) stored passwords.
63 void set_stored_password(char *host, char *port, char *username, char *password) {
65 char pwfile[PATH_MAX];
69 char hostbuf[256], portbuf[256], ubuf[256], pbuf[256];
71 determine_pwfilename(pwfile, sizeof pwfile);
72 if (IsEmptyStr(pwfile))
75 oldfp = fopen(pwfile, "r");
77 oldfp = fopen("/dev/null", "r");
80 fp = fopen(pwfile, "w");
82 fp = fopen("/dev/null", "w");
84 while (fgets(buf64, sizeof buf64, oldfp) != NULL) {
85 CtdlDecodeBase64(buf, buf64, sizeof(buf64));
86 extract_token(hostbuf, buf, 0, '|', sizeof hostbuf);
87 extract_token(portbuf, buf, 1, '|', sizeof portbuf);
88 extract_token(ubuf, buf, 2, '|', sizeof ubuf);
89 extract_token(pbuf, buf, 3, '|', sizeof pbuf);
91 if ((strcasecmp(hostbuf, host)) || (strcasecmp(portbuf, port))) {
92 snprintf(buf, sizeof buf, "%s|%s|%s|%s|", hostbuf, portbuf, ubuf, pbuf);
93 CtdlEncodeBase64(buf64, buf, strlen(buf), BASE64_NO_LINEBREAKS);
94 fprintf(fp, "%s\n", buf64);
97 if (!IsEmptyStr(username)) {
98 snprintf(buf, sizeof buf, "%s|%s|%s|%s|", host, port, username, password);
99 CtdlEncodeBase64(buf64, buf, strlen(buf), BASE64_NO_LINEBREAKS);
100 fprintf(fp, "%s\n", buf64);
108 // Set the password if the user wants to, clear it otherwise
109 void offer_to_remember_password(CtdlIPC * ipc, char *host, char *port, char *username, char *password) {
111 if (rc_remember_passwords) {
112 if (boolprompt("Remember username/password for this site", 0)) {
113 set_stored_password(host, port, username, password);
116 set_stored_password(host, port, "", "");