gwenhywfar 5.10.1
passwdstore.c
Go to the documentation of this file.
1/***************************************************************************
2 begin : Sat Dec 16 2012
3 copyright : (C) 2012 by Martin Preuss
4 email : martin@libchipcard.de
5
6 ***************************************************************************
7 * *
8 * This library is free software; you can redistribute it and/or *
9 * modify it under the terms of the GNU Lesser General Public *
10 * License as published by the Free Software Foundation; either *
11 * version 2.1 of the License, or (at your option) any later version. *
12 * *
13 * This library is distributed in the hope that it will be useful, *
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU *
16 * Lesser General Public License for more details. *
17 * *
18 * You should have received a copy of the GNU Lesser General Public *
19 * License along with this library; if not, write to the Free Software *
20 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, *
21 * MA 02111-1307 USA *
22 * *
23 ***************************************************************************/
24
25
26#ifdef HAVE_CONFIG_H
27# include <config.h>
28#endif
29
30#include "passwdstore_p.h"
31#include "i18n_l.h"
32
33#include <gwenhywfar/gui.h>
34#include <gwenhywfar/db.h>
35#include <gwenhywfar/directory.h>
36#include <gwenhywfar/fslock.h>
37#include <gwenhywfar/mdigest.h>
38#include <gwenhywfar/text.h>
39#include <gwenhywfar/debug.h>
40#include <gwenhywfar/smalltresor.h>
41
42#include <errno.h>
43
44
45
47{
49
51 if (fname)
52 sto->fileName=strdup(fname);
53 sto->dbPasswords=NULL;
54
55 return sto;
56}
57
58
59
61{
62 if (sto) {
63 memset(sto->pw, 0, sizeof(sto->pw));
64 if (sto->dbPasswords) {
66 GWEN_DB_Group_free(sto->dbPasswords);
67 sto->dbPasswords=NULL;
68 }
69 free(sto->fileName);
71 }
72}
73
74
75
77{
78 assert(sto);
79 memset(sto->pw, 0, GWEN_PASSWDSTORE_PWLEN);
80 if (sto->dbPasswords) {
82 GWEN_DB_Group_free(sto->dbPasswords);
83 sto->dbPasswords=NULL;
84 }
85}
86
87
88
89
90static int readFile(const char *fname, GWEN_BUFFER *dbuf)
91{
92 FILE *f;
93
94 f=fopen(fname, "rb");
95 if (f) {
96 while (!feof(f)) {
97 uint32_t l;
98 ssize_t s;
99 char *p;
100
101 GWEN_Buffer_AllocRoom(dbuf, 1024);
104 s=fread(p, 1, l, f);
105 if (s==0)
106 break;
107 if (s==(ssize_t)-1) {
109 "fread(%s): %s",
110 fname, strerror(errno));
111 fclose(f);
112 return GWEN_ERROR_IO;
113 }
114
117 }
118
119 fclose(f);
120 return 0;
121 }
122 else {
123 if (errno==ENOENT) {
124 DBG_INFO(GWEN_LOGDOMAIN, "File [%s] does not exist", fname);
126 }
127 else {
129 "fopen(%s): %s",
130 fname, strerror(errno));
131 return GWEN_ERROR_IO;
132 }
133 }
134}
135
136
137
138static int writeToFile(FILE *f, const char *p, int len)
139{
140 while (len>0) {
141 ssize_t l;
142 ssize_t s;
143
144 l=1024;
145 if (l>len)
146 l=len;
147 s=fwrite(p, 1, l, f);
148 if (s==(ssize_t)-1 || s==0) {
150 "fwrite: %s",
151 strerror(errno));
152 return GWEN_ERROR_IO;
153 }
154 p+=s;
155 len-=s;
156 }
157
158 return 0;
159}
160
161
162
163static int writeFile(const char *fname, const char *p, int len)
164{
165 FILE *f;
166
167 f=fopen(fname, "wb");
168 if (f) {
169 int rv;
170
171 rv=writeToFile(f, p, len);
172 if (rv<0) {
173 DBG_ERROR(GWEN_LOGDOMAIN, "here (%d)", rv);
174 fclose(f);
175 return rv;
176 }
177 if (fclose(f)) {
178 DBG_ERROR(GWEN_LOGDOMAIN, "here (%d)", rv);
179 return rv;
180 }
181 }
182 else {
183 DBG_ERROR(GWEN_LOGDOMAIN, "fopen(%s): %s",
184 fname, strerror(errno));
185 return GWEN_ERROR_IO;
186 }
187
188 return 0;
189}
190
191
192
193static int GWEN_PasswordStore_Digest(const uint8_t *t, uint32_t size, GWEN_BUFFER *buf)
194{
195 GWEN_MDIGEST *md;
196 int rv;
197
198 /* hash token and pin */
200 rv=GWEN_MDigest_Begin(md);
201 if (rv==0)
202 rv=GWEN_MDigest_Update(md, (const uint8_t *)t, size);
203 if (rv==0)
204 rv=GWEN_MDigest_End(md);
205 if (rv<0) {
206 DBG_ERROR(GWEN_LOGDOMAIN, "Hash error (%d)", rv);
208 return rv;
209 }
210
212 (const char *)GWEN_MDigest_GetDigestPtr(md),
215 return 0;
216}
217
218
219
220static int GWEN_PasswordStore_CheckDigest(const uint8_t *t, uint32_t size, const uint8_t *h)
221{
222 GWEN_MDIGEST *md;
223 int rv;
224
225 /* hash token and pin */
227 rv=GWEN_MDigest_Begin(md);
228 if (rv==0)
229 rv=GWEN_MDigest_Update(md, (const uint8_t *)t, size);
230 if (rv==0)
231 rv=GWEN_MDigest_End(md);
232 if (rv<0) {
233 DBG_ERROR(GWEN_LOGDOMAIN, "Hash error (%d)", rv);
235 return rv;
236 }
237
238 if (memcmp(h, GWEN_MDigest_GetDigestPtr(md), 20)) {
239 DBG_ERROR(GWEN_LOGDOMAIN, "Bad hash");
241 return GWEN_ERROR_BAD_DATA;
242 }
243
245 return 0;
246}
247
248
249
251{
252 if (sto->dbPasswords) {
254 GWEN_DB_Group_free(sto->dbPasswords);
255 sto->dbPasswords=NULL;
256 }
257}
258
259
260
262{
263 int rv;
264 GWEN_BUFFER *sbuf;
265
266 sbuf=GWEN_Buffer_new(0, 256, 0, 1);
267 rv=readFile(sto->fileName, sbuf);
268 if (rv<0) {
269 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
270 GWEN_Buffer_free(sbuf);
271 return rv;
272 }
273
274 if (GWEN_Buffer_GetUsedBytes(sbuf)<1) {
275 DBG_INFO(GWEN_LOGDOMAIN, "Empty file");
276 GWEN_Buffer_free(sbuf);
277 return GWEN_ERROR_NO_DATA;
278 }
279
280 for (;;) {
281 GWEN_BUFFER *tbuf;
282 uint32_t pos1;
283 uint32_t pos2;
284 uint32_t len;
285
286 tbuf=GWEN_Buffer_new(0, 256, 0, 1);
287 GWEN_Buffer_AppendString(tbuf, "PASSWORD_STORE_");
288 GWEN_Text_UnescapeToBufferTolerant(sto->fileName, tbuf);
289
290 if (sto->pw[0]==0) {
292 I18N("Enter Password"),
293 I18N("Please enter the password for the password store.\n"
294 "<html>"
295 "Please enter the password for the <b>password store</b>.</br>"
296 "</html>"),
297 sto->pw,
298 4,
299 sizeof(sto->pw)-1,
300 0);
301 if (rv<0) {
302 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
303 GWEN_Buffer_free(tbuf);
304 GWEN_Buffer_free(sbuf);
305 return rv;
306 }
307 }
308
309 pos1=GWEN_Buffer_GetPos(secbuf);
310
311 rv=GWEN_SmallTresor_Decrypt((const uint8_t *) GWEN_Buffer_GetStart(sbuf),
313 sto->pw,
314 secbuf,
315 GWEN_PASSWDSTORE_PW_ITERATIONS,
316 GWEN_PASSWDSTORE_CRYPT_ITERATIONS);
317 GWEN_Buffer_free(tbuf);
318 if (rv<0) {
319 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
320 /* error, reset password */
321 memset(sto->pw, 0, sizeof(sto->pw));
322 }
323 else {
324 /* check and remove hash */
325 pos2=GWEN_Buffer_GetPos(secbuf);
326 len=pos2-pos1;
327
328 if (len>=20) {
329 const uint8_t *p1;
330 const uint8_t *p2;
331
332 p1=(const uint8_t *)GWEN_Buffer_GetStart(secbuf)+pos1; /* start of decrypted data */
333 p2=(const uint8_t *)GWEN_Buffer_GetStart(secbuf)+(pos2-20); /* start of hash */
334
335 rv=GWEN_PasswordStore_CheckDigest(p1, len-20, p2);
336 if (rv<0) {
337 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
338 GWEN_Buffer_free(sbuf);
339 return rv;
340 }
341 else {
342 GWEN_Buffer_Crop(secbuf, 0, pos2-20);
343 break;
344 }
345 }
346 else {
347 DBG_ERROR(GWEN_LOGDOMAIN, "Bad data size (smaller than 20 bytes)");
348 /* reset buffer */
349 GWEN_Buffer_Crop(secbuf, 0, pos1);
350 GWEN_Buffer_free(sbuf);
351 return rv;
352 }
353 }
354 } /* for */
355
356 GWEN_Buffer_free(sbuf);
357
358 return 0;
359}
360
361
362
363static int GWEN_PasswordStore_EncryptWriteFile(GWEN_PASSWD_STORE *sto, const uint8_t *sec, uint32_t len)
364{
365 int rv;
366 GWEN_BUFFER *sbuf;
367 GWEN_BUFFER *tbuf;
368
369 /* make sure the data dir exists */
370 DBG_ERROR(0, "Looking for [%s]", sto->fileName);
372 if (rv<0) {
373 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
374 return rv;
375 }
376
377 tbuf=GWEN_Buffer_new(0, 256, 0, 1);
378 GWEN_Buffer_AppendString(tbuf, "PASSWORD_STORE_");
379 GWEN_Text_UnescapeToBufferTolerant(sto->fileName, tbuf);
380
381 /* ask for passwd if not already set */
382 if (sto->pw[0]==0) {
383 if (sto->isNew) {
385 I18N("Create New Password Store"),
386 I18N(
387 "You are about to create a new password store.\n"
388 "Passwords you store here will be encrypted with a passphrase\n"
389 "which you must enter now.\n"
390 "\n"
391
392 "Later you will only need to remember the passphrase for the\n"
393 "password store, not all the individuell passwords.\n"
394 "\n"
395 "WARNING: Storing your passwords in the password store\n"
396 "can be considered a security risk, especially if the passphrase protecting it\n"
397 "is not strong enough!\n"
398 "\n"
399 "You can safely abort this step, in which case your passwords will not be stored.\n"
400 "\n"
401 "Please enter the passphrase for the password store to be created or abort.\n"
402 "<html>"
403 "<p>You are about to create a new <b>password store</b>.</p>"
404 "<br>"
405 "<p>Passwords you store here will be encrypted with a passphrase "
406 "which you must enter now.</p>"
407 "<p>Later you will only need to remember the passphrase for the "
408 "password store, not all the individuell passwords.<p>"
409 "<p><font color=\"red\">"
410 "<b>Warning:</b> Storing your passwords in the password store "
411 "can be considered a <b>security risk</b>, especially if the passphrase protecting it "
412 "is not strong enough!"
413 "</font></p>"
414 "<p><b>You can safely abort this step</b>, in which case your passwords will not be stored.</p>"
415 "<br>"
416 "<p>Please enter the passphrase for the password store to be created or abort.</p>"
417 "</html>"),
418 sto->pw,
419 4,
420 sizeof(sto->pw)-1,
421 0);
422
423 }
424 else
426 I18N("Enter Password"),
427 I18N("Please enter the password for the password store.\n"
428 "<html>"
429 "Please enter the password for the <b>password store</b>.</br>"
430 "</html>"),
431 sto->pw,
432 4,
433 sizeof(sto->pw)-1,
434 0);
435 if (rv<0) {
436 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
437 GWEN_Buffer_free(tbuf);
438 return rv;
439 }
440 }
441
442 GWEN_Buffer_free(tbuf);
443
444 /* prepare data to write */
445 sbuf=GWEN_Buffer_new(0, 256, 0, 1);
446 tbuf=GWEN_Buffer_new(0, len+20, 0, 1);
447
448 /* add clear text data */
449 GWEN_Buffer_AppendBytes(tbuf, (const char *) sec, len);
450
451 /* add hash (20 bytes) */
452 rv=GWEN_PasswordStore_Digest((const uint8_t *) sec, len, tbuf);
453 if (rv<0) {
454 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
455 GWEN_Buffer_free(tbuf);
456 GWEN_Buffer_free(sbuf);
457 return rv;
458 }
459
460 /* encrypt cleartext */
461 rv=GWEN_SmallTresor_Encrypt((const uint8_t *) GWEN_Buffer_GetStart(tbuf),
463 sto->pw,
464 sbuf,
465 GWEN_PASSWDSTORE_PW_ITERATIONS,
466 GWEN_PASSWDSTORE_CRYPT_ITERATIONS);
467 if (rv<0) {
468 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
469 GWEN_Buffer_free(tbuf);
470 GWEN_Buffer_free(sbuf);
471 return rv;
472 }
474 GWEN_Buffer_free(tbuf);
475
476 /* write file */
477 rv=writeFile(sto->fileName,
480 if (rv<0) {
481 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
482 GWEN_Buffer_free(sbuf);
483 return rv;
484 }
485
486 GWEN_Buffer_free(sbuf);
487
488 return 0;
489}
490
491
492
493
495{
496 GWEN_BUFFER *tbuf;
497 int rv;
498
499 tbuf=GWEN_Buffer_new(0, 256, 0, 1);
500
502 if (rv<0) {
503 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
504 GWEN_Buffer_free(tbuf);
505 return rv;
506 }
507 sto->isNew=0;
508
510
511 sto->dbPasswords=GWEN_DB_Group_new("passwords");
512 rv=GWEN_DB_ReadFromString(sto->dbPasswords,
516 if (rv<0) {
517 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
519 GWEN_Buffer_free(tbuf);
520 return rv;
521 }
523
525 GWEN_Buffer_free(tbuf);
526 return 0;
527}
528
529
530
532{
533 if (sto->dbPasswords) {
534 GWEN_BUFFER *tbuf;
535 int rv;
536
537 tbuf=GWEN_Buffer_new(0, 256, 0, 1);
538 rv=GWEN_DB_WriteToBuffer(sto->dbPasswords, tbuf, GWEN_DB_FLAGS_DEFAULT);
539 if (rv<0) {
540 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
542 GWEN_Buffer_free(tbuf);
543 return rv;
544 }
545
547 (const uint8_t *) GWEN_Buffer_GetStart(tbuf),
549 if (rv<0) {
550 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
552 GWEN_Buffer_free(tbuf);
553 return rv;
554 }
555
557 GWEN_Buffer_free(tbuf);
558 return 0;
559 }
560 else {
561 DBG_INFO(GWEN_LOGDOMAIN, "No password db");
562 return GWEN_ERROR_INTERNAL;
563 }
564}
565
566
567
568
569static int GWEN_PasswordStore__SetPassword(GWEN_PASSWD_STORE *sto, const char *token, const char *secret)
570{
571 GWEN_BUFFER *buf;
572
573 buf=GWEN_Buffer_new(0, 64, 0, 1);
575
576 if (secret==NULL)
577 GWEN_DB_DeleteVar(sto->dbPasswords, GWEN_Buffer_GetStart(buf));
578 else
580 GWEN_Buffer_GetStart(buf), secret);
582 GWEN_Buffer_free(buf);
583
584 return 0;
585}
586
587
588
589static int GWEN_PasswordStore__GetPassword(GWEN_PASSWD_STORE *sto, const char *token, char *buffer, int minLen,
590 int maxLen)
591{
592 GWEN_BUFFER *buf;
593 const char *s;
594
595 buf=GWEN_Buffer_new(0, 256, 0, 1);
597
598 s=GWEN_DB_GetCharValue(sto->dbPasswords,
600 0, NULL);
601 if (s) {
602 int i;
603
604 i=strlen(s);
605 if (i>=minLen && i < maxLen) {
606 memmove(buffer, s, i+1);
607 GWEN_Buffer_free(buf);
608 return 0;
609 }
610 else {
611 DBG_ERROR(GWEN_LOGDOMAIN, "Stored password [%s] is not within size limits (%d), rejecting.",
612 GWEN_Buffer_GetStart(buf), i);
613 }
614 }
615
616 GWEN_Buffer_free(buf);
618}
619
620
621
622
623
624int GWEN_PasswordStore_SetPassword(GWEN_PASSWD_STORE *sto, const char *token, const char *secret)
625{
626 GWEN_FSLOCK *lck;
628 int rv;
629
630 /* make sure path exists */
632 if (rv<0) {
633 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
634 return rv;
635 }
636
637 /* lock file */
638 lck=GWEN_FSLock_new(sto->fileName, GWEN_FSLock_TypeFile);
639 rs=GWEN_FSLock_Lock(lck, 60*1000, 0);
640 if (rs!=GWEN_FSLock_ResultOk) {
641 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rs);
642 return GWEN_ERROR_IO;
643 }
644
645 /* read and decrypt file */
647 if (rv<0) {
649 DBG_INFO(GWEN_LOGDOMAIN, "Will create password store [%s]", sto->fileName);
650 if (sto->dbPasswords==NULL) {
651 sto->dbPasswords=GWEN_DB_Group_new("passwords");
653 }
654 sto->isNew=1;
655 }
656 else {
657 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
659 GWEN_FSLock_free(lck);
660 return rv;
661 }
662 }
663
664 /* set password in db */
665 rv=GWEN_PasswordStore__SetPassword(sto, token, secret);
666 if (rv<0) {
667 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
669 GWEN_FSLock_free(lck);
670 return rv;
671 }
672
673 /* write file back */
675 if (rv<0) {
676 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
678 GWEN_FSLock_free(lck);
679 return rv;
680 }
681
682 /* unlock file */
684 GWEN_FSLock_free(lck);
685
686 /* release passwords */
688
689 return 0;
690}
691
692
693
694
695int GWEN_PasswordStore_GetPassword(GWEN_PASSWD_STORE *sto, const char *token, char *buffer, int minLen, int maxLen)
696{
697 int rv;
698 GWEN_FSLOCK *lck;
700
701 /* make sure path exists */
703 if (rv<0) {
704 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
705 return rv;
706 }
707
708 /* lock file */
709 lck=GWEN_FSLock_new(sto->fileName, GWEN_FSLock_TypeFile);
710 rs=GWEN_FSLock_Lock(lck, 60*1000, 0);
711 if (rs!=GWEN_FSLock_ResultOk) {
712 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rs);
713 return GWEN_ERROR_IO;
714 }
715
716 /* read and decode file */
718 if (rv<0) {
719 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
721 GWEN_FSLock_free(lck);
722 return rv;
723 }
724
725 /* unlock file */
727 GWEN_FSLock_free(lck);
728
729 /* finally get password, if possible */
730 rv=GWEN_PasswordStore__GetPassword(sto, token, buffer, minLen, maxLen);
731 if (rv<0) {
732 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
733 return rv;
734 }
735
736 /* release passwords */
738
739 return 0;
740}
741
742
743
745{
746 int rv;
747 GWEN_FSLOCK *lck;
749 int pwErrors;
750 GWEN_DB_NODE *dbVar;
751
752 /* make sure path exists */
754 if (rv<0) {
755 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
756 return rv;
757 }
758
759 /* lock file */
760 lck=GWEN_FSLock_new(sto->fileName, GWEN_FSLock_TypeFile);
761 rs=GWEN_FSLock_Lock(lck, 60*1000, 0);
762 if (rs!=GWEN_FSLock_ResultOk) {
763 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rs);
764 return GWEN_ERROR_IO;
765 }
766
767 /* read and decode file */
769 if (rv<0) {
770 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
772 GWEN_FSLock_free(lck);
773 return rv;
774 }
775
776 /* unlock file */
778 GWEN_FSLock_free(lck);
779
780
781 /* read list of tokens from the file */
782 pwErrors=0;
783 dbVar=GWEN_DB_GetFirstVar(sto->dbPasswords);
784 while (dbVar) {
785 const char *s;
786
787 s=GWEN_DB_VariableName(dbVar);
788 if (s && *s) {
789 GWEN_BUFFER *buf;
790 int rv;
791
792 buf=GWEN_Buffer_new(0, 256, 0, 1);
794 if (rv<0) {
795 DBG_ERROR(GWEN_LOGDOMAIN, "Error unescaping token name (%d), ignoring", rv);
796 pwErrors++;
797 }
798 else {
800 }
801 GWEN_Buffer_free(buf);
802 }
803 else
804 pwErrors++;
805
806 dbVar=GWEN_DB_GetNextVar(dbVar);
807 }
808
809 /* release passwords */
811
812 if (pwErrors) {
813 DBG_ERROR(GWEN_LOGDOMAIN, "Got %d errors.", pwErrors);
814 return GWEN_ERROR_GENERIC;
815 }
816
817 return 0;
818}
819
820
821
822
#define NULL
Definition: binreloc.c:300
GWEN_BUFFER * GWEN_Buffer_new(char *buffer, uint32_t size, uint32_t used, int take)
Definition: buffer.c:42
int GWEN_Buffer_IncrementPos(GWEN_BUFFER *bf, uint32_t i)
Definition: buffer.c:452
uint32_t GWEN_Buffer_GetMaxUnsegmentedWrite(GWEN_BUFFER *bf)
Definition: buffer.c:528
int GWEN_Buffer_AdjustUsedBytes(GWEN_BUFFER *bf)
Definition: buffer.c:469
char * GWEN_Buffer_GetPosPointer(const GWEN_BUFFER *bf)
Definition: buffer.c:549
void GWEN_Buffer_OverwriteContent(GWEN_BUFFER *bf, int c)
Definition: buffer.c:557
int GWEN_Buffer_AppendBytes(GWEN_BUFFER *bf, const char *buffer, uint32_t size)
Definition: buffer.c:361
uint32_t GWEN_Buffer_GetPos(const GWEN_BUFFER *bf)
Definition: buffer.c:253
void GWEN_Buffer_free(GWEN_BUFFER *bf)
Definition: buffer.c:89
int GWEN_Buffer_AppendString(GWEN_BUFFER *bf, const char *buffer)
Definition: buffer.c:989
uint32_t GWEN_Buffer_GetUsedBytes(const GWEN_BUFFER *bf)
Definition: buffer.c:277
char * GWEN_Buffer_GetStart(const GWEN_BUFFER *bf)
Definition: buffer.c:235
int GWEN_Buffer_AllocRoom(GWEN_BUFFER *bf, uint32_t size)
Definition: buffer.c:285
int GWEN_Buffer_Crop(GWEN_BUFFER *bf, uint32_t pos, uint32_t l)
Definition: buffer.c:947
const char * GWEN_DB_GetCharValue(GWEN_DB_NODE *n, const char *path, int idx, const char *defVal)
Definition: db.c:971
int GWEN_DB_DeleteVar(GWEN_DB_NODE *n, const char *path)
Definition: db.c:899
GWEN_DB_NODE * GWEN_DB_GetNextVar(GWEN_DB_NODE *n)
Definition: db.c:500
GWEN_DB_NODE * GWEN_DB_Group_new(const char *name)
Definition: db.c:173
GWEN_DB_NODE * GWEN_DB_GetFirstVar(GWEN_DB_NODE *n)
Definition: db.c:479
int GWEN_DB_SetCharValue(GWEN_DB_NODE *n, uint32_t flags, const char *path, const char *val)
Definition: db.c:997
const char * GWEN_DB_VariableName(GWEN_DB_NODE *n)
Definition: db.c:1928
void GWEN_DB_ModifyBranchFlagsDown(GWEN_DB_NODE *n, uint32_t newflags, uint32_t mask)
Definition: db.c:1805
void GWEN_DB_Group_free(GWEN_DB_NODE *n)
Definition: db.c:421
GWENHYWFAR_API int GWEN_DB_ReadFromString(GWEN_DB_NODE *n, const char *str, int len, uint32_t dbflags)
Definition: dbrw.c:1035
GWENHYWFAR_API int GWEN_DB_WriteToBuffer(GWEN_DB_NODE *n, GWEN_BUFFER *buf, uint32_t dbflags)
Definition: dbrw.c:1061
#define GWEN_DB_FLAGS_DEFAULT
Definition: db.h:168
#define GWEN_DB_FLAGS_OVERWRITE_VARS
Definition: db.h:121
#define GWEN_DB_NODE_FLAGS_SAFE
Definition: db.h:214
struct GWEN_DB_NODE GWEN_DB_NODE
Definition: db.h:228
#define DBG_INFO(dbg_logger, format, args...)
Definition: debug.h:181
#define DBG_ERROR(dbg_logger, format, args...)
Definition: debug.h:97
GWENHYWFAR_API int GWEN_Directory_GetPath(const char *path, unsigned int flags)
#define I18N(m)
Definition: error.c:42
#define GWEN_ERROR_INTERNAL
Definition: error.h:125
#define GWEN_ERROR_BAD_DATA
Definition: error.h:121
#define GWEN_ERROR_IO
Definition: error.h:123
#define GWEN_ERROR_GENERIC
Definition: error.h:62
#define GWEN_ERROR_NOT_FOUND
Definition: error.h:89
#define GWEN_ERROR_NO_DATA
Definition: error.h:94
GWENHYWFAR_API void GWEN_FSLock_free(GWEN_FSLOCK *fl)
struct GWEN_FSLOCK GWEN_FSLOCK
Definition: fslock.h:59
GWENHYWFAR_API GWEN_FSLOCK * GWEN_FSLock_new(const char *fname, GWEN_FSLOCK_TYPE t)
GWEN_FSLOCK_RESULT
Definition: fslock.h:71
@ GWEN_FSLock_ResultOk
Definition: fslock.h:72
GWENHYWFAR_API GWEN_FSLOCK_RESULT GWEN_FSLock_Lock(GWEN_FSLOCK *fl, int timeout, uint32_t gid)
@ GWEN_FSLock_TypeFile
Definition: fslock.h:66
GWENHYWFAR_API GWEN_FSLOCK_RESULT GWEN_FSLock_Unlock(GWEN_FSLOCK *fl)
struct GWEN_BUFFER GWEN_BUFFER
A dynamically resizeable text buffer.
Definition: buffer.h:38
GWENHYWFAR_API int GWEN_Gui_InputBox(uint32_t flags, const char *title, const char *text, char *buffer, int minLen, int maxLen, uint32_t guiid)
Definition: gui_virtual.c:360
#define GWEN_GUI_INPUT_FLAGS_DIRECT
Definition: gui.h:226
#define GWEN_GUI_INPUT_FLAGS_CONFIRM
Definition: gui.h:211
#define GWEN_LOGDOMAIN
Definition: logger.h:35
int GWEN_MDigest_Begin(GWEN_MDIGEST *md)
Definition: mdigest.c:129
int GWEN_MDigest_End(GWEN_MDIGEST *md)
Definition: mdigest.c:141
unsigned int GWEN_MDigest_GetDigestSize(GWEN_MDIGEST *md)
Definition: mdigest.c:90
uint8_t * GWEN_MDigest_GetDigestPtr(GWEN_MDIGEST *md)
Definition: mdigest.c:81
void GWEN_MDigest_free(GWEN_MDIGEST *md)
Definition: mdigest.c:54
int GWEN_MDigest_Update(GWEN_MDIGEST *md, const uint8_t *buf, unsigned int l)
Definition: mdigest.c:153
GWENHYWFAR_API GWEN_MDIGEST * GWEN_MDigest_Rmd160_new(void)
Definition: mdigestgc.c:158
struct GWEN_MDIGEST GWEN_MDIGEST
Definition: mdigest.h:25
#define GWEN_FREE_OBJECT(varname)
Definition: memory.h:61
#define GWEN_NEW_OBJECT(typ, varname)
Definition: memory.h:55
int GWEN_PasswordStore_GetPassword(GWEN_PASSWD_STORE *sto, const char *token, char *buffer, int minLen, int maxLen)
Definition: passwdstore.c:695
static int GWEN_PasswordStore__GetPassword(GWEN_PASSWD_STORE *sto, const char *token, char *buffer, int minLen, int maxLen)
Definition: passwdstore.c:589
static int readFile(const char *fname, GWEN_BUFFER *dbuf)
Definition: passwdstore.c:90
GWEN_PASSWD_STORE * GWEN_PasswordStore_new(const char *fname)
Definition: passwdstore.c:46
static int GWEN_PasswordStore_CheckDigest(const uint8_t *t, uint32_t size, const uint8_t *h)
Definition: passwdstore.c:220
void GWEN_PasswordStore_ClearStoragePasswd(GWEN_PASSWD_STORE *sto)
Definition: passwdstore.c:76
int GWEN_PasswordStore_GetTokenList(GWEN_PASSWD_STORE *sto, GWEN_STRINGLIST *sl)
Definition: passwdstore.c:744
static int GWEN_PasswordStore__SetPassword(GWEN_PASSWD_STORE *sto, const char *token, const char *secret)
Definition: passwdstore.c:569
static int GWEN_PasswordStore_EncryptWriteFile(GWEN_PASSWD_STORE *sto, const uint8_t *sec, uint32_t len)
Definition: passwdstore.c:363
static int writeToFile(FILE *f, const char *p, int len)
Definition: passwdstore.c:138
void GWEN_PasswordStore_free(GWEN_PASSWD_STORE *sto)
Definition: passwdstore.c:60
static int GWEN_PasswordStore_ReadDecryptFile(GWEN_PASSWD_STORE *sto, GWEN_BUFFER *secbuf)
Definition: passwdstore.c:261
static void GWEN_PasswordStore_SafeFreeDb(GWEN_PASSWD_STORE *sto)
Definition: passwdstore.c:250
int GWEN_PasswordStore_SetPassword(GWEN_PASSWD_STORE *sto, const char *token, const char *secret)
Definition: passwdstore.c:624
static int GWEN_PasswordStore_WriteFile(GWEN_PASSWD_STORE *sto)
Definition: passwdstore.c:531
static int writeFile(const char *fname, const char *p, int len)
Definition: passwdstore.c:163
static int GWEN_PasswordStore_Digest(const uint8_t *t, uint32_t size, GWEN_BUFFER *buf)
Definition: passwdstore.c:193
static int GWEN_PasswordStore_ReadFile(GWEN_PASSWD_STORE *sto)
Definition: passwdstore.c:494
struct GWEN_PASSWD_STORE GWEN_PASSWD_STORE
Definition: passwdstore.h:37
#define GWEN_PATH_FLAGS_VARIABLE
Definition: path.h:111
int GWEN_SmallTresor_Encrypt(const uint8_t *src, uint32_t slen, const char *password, GWEN_BUFFER *dst, int passwordIterations, int cryptIterations)
Definition: smalltresor.c:239
int GWEN_SmallTresor_Decrypt(const uint8_t *p, uint32_t len, const char *password, GWEN_BUFFER *dst, int passwordIterations, int cryptIterations)
Definition: smalltresor.c:346
int GWEN_StringList_AppendString(GWEN_STRINGLIST *sl, const char *s, int take, int checkDouble)
Definition: stringlist.c:245
struct GWEN_STRINGLISTSTRUCT GWEN_STRINGLIST
Definition: stringlist.h:56
int GWEN_Text_EscapeToBufferTolerant(const char *src, GWEN_BUFFER *buf)
Definition: text.c:1471
int GWEN_Text_UnescapeToBufferTolerant(const char *src, GWEN_BUFFER *buf)
Definition: text.c:1515