1 /* 2 KeePass Password Safe - The Open-Source Password Manager 3 Copyright (C) 2003-2021 Dominik Reichl <dominik.reichl@t-online.de> 4 5 This program is free software; you can redistribute it and/or modify 6 it under the terms of the GNU General Public License as published by 7 the Free Software Foundation; either version 2 of the License, or 8 (at your option) any later version. 9 10 This program is distributed in the hope that it will be useful, 11 but WITHOUT ANY WARRANTY; without even the implied warranty of 12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 GNU General Public License for more details. 14 15 You should have received a copy of the GNU General Public License 16 along with this program; if not, write to the Free Software 17 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA 18 */ 19 20 using System; 21 using System.Collections.Generic; 22 using System.Diagnostics; 23 using System.Drawing; 24 using System.Globalization; 25 using System.IO; 26 using System.Text; 27 28 using KeePass.Resources; 29 30 using KeePassLib; 31 using KeePassLib.Interfaces; 32 using KeePassLib.Security; 33 using KeePassLib.Utility; 34 35 namespace KeePass.DataExchange.Formats 36 { 37 // 1.44 & Pro 1.07 38 internal sealed class AnyPwCsv144 : FileFormatProvider 39 { 40 public override bool SupportsImport { get { return true; } } 41 public override bool SupportsExport { get { return false; } } 42 43 public override string FormatName { get { return "Any Password CSV"; } } 44 public override string DefaultExtension { get { return "csv"; } } 45 public override string ApplicationGroup { get { return KPRes.PasswordManagers; } } 46 47 public override bool ImportAppendsToRootGroupOnly { get { return true; } } 48 49 public override Image SmallIcon 50 { 51 get { return KeePass.Properties.Resources.B16x16_Imp_AnyPw; } 52 } 53 Import(PwDatabase pwStorage, Stream sInput, IStatusLogger slLogger)54 public override void Import(PwDatabase pwStorage, Stream sInput, 55 IStatusLogger slLogger) 56 { 57 StreamReader sr = new StreamReader(sInput, Encoding.Default); 58 string strData = sr.ReadToEnd(); 59 sr.Close(); 60 61 string[] vLines = strData.Split(new char[] { '\r', '\n' }, 62 StringSplitOptions.RemoveEmptyEntries); 63 64 foreach(string strLine in vLines) 65 { 66 if(strLine.Length > 5) ProcessCsvLine(strLine, pwStorage); 67 } 68 } 69 ProcessCsvLine(string strLine, PwDatabase pwStorage)70 private static void ProcessCsvLine(string strLine, PwDatabase pwStorage) 71 { 72 List<string> list = ImportUtil.SplitCsvLine(strLine, ","); 73 Debug.Assert((list.Count == 6) || (list.Count == 7)); 74 if(list.Count < 6) return; 75 bool bIsPro = (list.Count >= 7); // Std exports 6 fields only 76 77 PwEntry pe = new PwEntry(true, true); 78 pwStorage.RootGroup.AddEntry(pe, true); 79 80 pe.Strings.Set(PwDefs.TitleField, new ProtectedString( 81 pwStorage.MemoryProtection.ProtectTitle, 82 ParseCsvWord(list[0], false))); 83 pe.Strings.Set(PwDefs.UserNameField, new ProtectedString( 84 pwStorage.MemoryProtection.ProtectUserName, 85 ParseCsvWord(list[1], false))); 86 pe.Strings.Set(PwDefs.PasswordField, new ProtectedString( 87 pwStorage.MemoryProtection.ProtectPassword, 88 ParseCsvWord(list[2], false))); 89 pe.Strings.Set(PwDefs.UrlField, new ProtectedString( 90 pwStorage.MemoryProtection.ProtectUrl, 91 ParseCsvWord(list[3], false))); 92 93 int p = 3; 94 if(bIsPro) 95 pe.Strings.Set(KPRes.Custom, new ProtectedString(false, 96 ParseCsvWord(list[++p], false))); 97 98 pe.Strings.Set(PwDefs.NotesField, new ProtectedString( 99 pwStorage.MemoryProtection.ProtectNotes, 100 ParseCsvWord(list[++p], true))); 101 102 DateTime dt; 103 if(DateTime.TryParse(ParseCsvWord(list[++p], false), out dt)) 104 pe.CreationTime = pe.LastAccessTime = pe.LastModificationTime = 105 TimeUtil.ToUtc(dt, false); 106 else { Debug.Assert(false); } 107 } 108 ParseCsvWord(string strWord, bool bFixCodes)109 private static string ParseCsvWord(string strWord, bool bFixCodes) 110 { 111 string str = strWord.Trim(); 112 113 if((str.Length >= 2) && str.StartsWith("\"") && str.EndsWith("\"")) 114 str = str.Substring(1, str.Length - 2); 115 116 str = str.Replace("\"\"", "\""); 117 118 if(bFixCodes) 119 { 120 str = str.Replace("<13>", string.Empty); 121 str = str.Replace("<10>", "\r\n"); 122 } 123 124 return str; 125 } 126 } 127 } 128