diff --git a/KeePass2PCL.Test.Desktop/KeePass2PCL.Test.Desktop.csproj b/KeePass2PCL.Test.Desktop/KeePass2PCL.Test.Desktop.csproj new file mode 100644 index 0000000..e7ca24b --- /dev/null +++ b/KeePass2PCL.Test.Desktop/KeePass2PCL.Test.Desktop.csproj @@ -0,0 +1,102 @@ + + + + + Debug + AnyCPU + {0BD8B544-EB60-461F-9A71-605A6DFCBB19} + Library + KeePass2PCL.Test.Desktop + KeePass2PCL.Test.Desktop + v4.5 + + + + + true + full + false + bin\Debug + DEBUG; + prompt + 4 + false + + + full + true + bin\Release + prompt + 4 + false + + + + ..\packages\Castle.Core.4.1.1\lib\net45\Castle.Core.dll + + + + + ..\packages\Moq.4.7.99\lib\net45\Moq.dll + + + ..\packages\NUnit.3.7.1\lib\net45\nunit.framework.dll + + + ..\packages\PCLCrypto.2.0.147\lib\net45\PCLCrypto.dll + + + ..\packages\PInvoke.BCrypt.0.5.97\lib\net45\PInvoke.BCrypt.dll + + + ..\packages\PInvoke.Kernel32.0.5.97\lib\net45\PInvoke.Kernel32.dll + + + ..\packages\PInvoke.NCrypt.0.5.97\lib\net45\PInvoke.NCrypt.dll + + + ..\packages\PInvoke.Windows.Core.0.5.97\lib\net35\PInvoke.Windows.Core.dll + + + ..\packages\Splat.GtkSharp.1.6.2\lib\net45\Splat.dll + + + + ..\packages\PCLStorage.1.0.2\lib\net45\PCLStorage.dll + + + ..\packages\PCLStorage.1.0.2\lib\net45\PCLStorage.Abstractions.dll + + + ..\packages\Mono.Security.3.2.3.0\lib\net45\Mono.Security.dll + + + + + ..\packages\Validation.2.4.15\lib\net45\Validation.dll + + + + + + + + + + + + + + {2e710089-9559-4967-846c-e763dd1f3acb} + KeePass2PCL + + + + + + This project references NuGet package(s) that are missing on this computer. Use NuGet Package Restore to download them. For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}. + + + + + \ No newline at end of file diff --git a/KeePass2PCL.Test.Desktop/app.config b/KeePass2PCL.Test.Desktop/app.config new file mode 100644 index 0000000..6d631fa --- /dev/null +++ b/KeePass2PCL.Test.Desktop/app.config @@ -0,0 +1,19 @@ + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/KeePass2PCL.Test.Desktop/packages.config b/KeePass2PCL.Test.Desktop/packages.config new file mode 100644 index 0000000..57fbffd --- /dev/null +++ b/KeePass2PCL.Test.Desktop/packages.config @@ -0,0 +1,18 @@ + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/KeePass2PCL.Test.Shared/Cryptography/Cipher/StandardAesEngineTests.cs b/KeePass2PCL.Test.Shared/Cryptography/Cipher/StandardAesEngineTests.cs new file mode 100644 index 0000000..b248752 --- /dev/null +++ b/KeePass2PCL.Test.Shared/Cryptography/Cipher/StandardAesEngineTests.cs @@ -0,0 +1,65 @@ +using System; +using System.IO; + +#if KeePassLib +using KeePassLib.Cryptography.Cipher; +#else +using KeePass2PCL.Cryptography.Cipher; +#endif + +using NUnit.Framework; + +namespace KeePass2PCL.Test.Shared.Cryptography.Cipher +{ + [TestFixture ()] + public class StandardAesEngineTests + { + [Test ()] + public void TestEncryptStream () + { + // Test vector (official ECB test vector #356) + var pbIV = new byte[16]; + var pbTestKey = new byte[32]; + var pbTestData = new byte[16]; + var pbReferenceCT = new byte[16] { + 0x75, 0xD1, 0x1B, 0x0E, 0x3A, 0x68, 0xC4, 0x22, + 0x3D, 0x88, 0xDB, 0xF0, 0x17, 0x97, 0x7D, 0xD7 + }; + + pbTestData[0] = 0x04; + + var outStream = new MemoryStream (new byte[16]); + var aes = new StandardAesEngine (); + var inStream = aes.EncryptStream (outStream, pbTestKey, pbIV); + new BinaryWriter (inStream).Write (pbTestData); + Assert.That (outStream.Position, Is.EqualTo (16)); + outStream.Position = 0; + var outBytes = new BinaryReader (outStream).ReadBytes (16); + Assert.That(outBytes, Is.EqualTo (pbReferenceCT)); + } + + [Test ()] + public void TestDecryptStream () + { + // Test vector (official ECB test vector #356) + var pbIV = new byte[16]; + var pbTestKey = new byte[32]; + var pbTestData = new byte[16]; + var pbReferenceCT = new byte[16] { + 0x75, 0xD1, 0x1B, 0x0E, 0x3A, 0x68, 0xC4, 0x22, + 0x3D, 0x88, 0xDB, 0xF0, 0x17, 0x97, 0x7D, 0xD7 + }; + + pbTestData[0] = 0x04; + + // Possible Mono Bug? This only works with size >= 48 + var inStream = new MemoryStream (new byte[48]); + inStream.Write (pbReferenceCT, 0, pbReferenceCT.Length); + inStream.Position = 0; + var aes = new StandardAesEngine (); + var outStream = aes.DecryptStream (inStream, pbTestKey, pbIV); + var outBytes = new BinaryReader (outStream).ReadBytes (16); + Assert.That(outBytes, Is.EqualTo (pbTestData)); + } + } +} diff --git a/KeePass2PCL.Test.Shared/Cryptography/CryptoRandomStreamTests.cs b/KeePass2PCL.Test.Shared/Cryptography/CryptoRandomStreamTests.cs new file mode 100644 index 0000000..cf585f2 --- /dev/null +++ b/KeePass2PCL.Test.Shared/Cryptography/CryptoRandomStreamTests.cs @@ -0,0 +1,60 @@ +using NUnit.Framework; +using System; + +#if KeePassLib +using KeePassLib.Cryptography; +#else +using ModernKeePassLibPCL.Cryptography; +#endif + +namespace KeePass2PCL.Test.Shared.Cryptography +{ + [TestFixture ()] + public class CryptoRandomStreamTests + { + void TestGetRandomBytes(CryptoRandomStream stream) + { + const uint length = 16; + var bytes1 = stream.GetRandomBytes (length); + Assert.That (bytes1.Length, Is.EqualTo (length)); + var bytes2 = stream.GetRandomBytes (length); + Assert.That (bytes2, Is.Not.EqualTo (bytes1)); + } + + [Test ()] + public void TestGetRandomBytesCrsAlgorithmSalsa20 () + { + var stream = new CryptoRandomStream (CrsAlgorithm.Salsa20, new byte[16]); + TestGetRandomBytes (stream); + } + + [Test ()] + public void TestGetRandomBytesCrsAlgorithmArcFourVariant () + { + var stream = new CryptoRandomStream (CrsAlgorithm.ArcFourVariant, new byte[16]); + TestGetRandomBytes (stream); + } + + void TestGetRandomInt64 (CryptoRandomStream stream) + { + var value1 = stream.GetRandomUInt64 (); + var value2 = stream.GetRandomUInt64 (); + Assert.That (value2, Is.Not.EqualTo (value1)); + } + + [Test ()] + public void TestGetRandomInt64AlgorithmSalsa20 () + { + var stream = new CryptoRandomStream (CrsAlgorithm.Salsa20, new byte[16]); + TestGetRandomInt64 (stream); + } + + [Test ()] + public void TestGetRandomInt64AlgorithmArcFourVariant () + { + var stream = new CryptoRandomStream (CrsAlgorithm.ArcFourVariant, new byte[16]); + TestGetRandomInt64 (stream); + } + } +} + diff --git a/KeePass2PCL.Test.Shared/Cryptography/CryptoRandomTests.cs b/KeePass2PCL.Test.Shared/Cryptography/CryptoRandomTests.cs new file mode 100644 index 0000000..90d8db8 --- /dev/null +++ b/KeePass2PCL.Test.Shared/Cryptography/CryptoRandomTests.cs @@ -0,0 +1,44 @@ +using NUnit.Framework; +using System; + +#if KeePassLib +using KeePassLib.Cryptography; +#else +using KeePass2PCL.Cryptography; +#endif + +namespace KeePass2PCL.Test.Shared.Cryptography +{ + [TestFixture ()] + public class CryptoRandomTests + { + [Test ()] + public void TestAddEntropy () + { + // just making sure it does not throw an exception + CryptoRandom.Instance.AddEntropy (new byte[1]); + } + + [Test ()] + public void TestGetRandomBytes () + { + const int length = 32; + var bytes1 = CryptoRandom.Instance.GetRandomBytes (length); + Assert.That (bytes1.Length, Is.EqualTo (length)); + var bytes2 = CryptoRandom.Instance.GetRandomBytes (length); + Assert.That (bytes2, Is.Not.EqualTo (bytes1)); + } + + [Test ()] + public void TestGeneratedBytesCount () + { + const int length = 1; + CryptoRandom.Instance.GetRandomBytes (length); + var count1 = CryptoRandom.Instance.GeneratedBytesCount; + CryptoRandom.Instance.GetRandomBytes (length); + var count2 = CryptoRandom.Instance.GeneratedBytesCount; + Assert.That (count2, Is.GreaterThan (count1)); + } + } +} + diff --git a/KeePass2PCL.Test.Shared/Cryptography/HashingStreamExTests.cs b/KeePass2PCL.Test.Shared/Cryptography/HashingStreamExTests.cs new file mode 100644 index 0000000..8db9b59 --- /dev/null +++ b/KeePass2PCL.Test.Shared/Cryptography/HashingStreamExTests.cs @@ -0,0 +1,77 @@ +using NUnit.Framework; +using System; +using System.IO; +using System.Text; + +#if KeePassLib +using KeePassLib.Cryptography; +#else +using KeePass2PCL.Cryptography; +#endif + +namespace KeePass2PCL.Test.Shared.Cryptography +{ + [TestFixture ()] + public class HashingStreamExTests + { + const string data = "test"; + + // The expected hash includes the \n added by WriteLine + static readonly byte[] sha256HashOfData = { + 0xf2, 0xca, 0x1b, 0xb6, 0xc7, 0xe9, 0x07, 0xd0, + 0x6d, 0xaf, 0xe4, 0x68, 0x7e, 0x57, 0x9f, 0xce, + 0x76, 0xb3, 0x7e, 0x4e, 0x93, 0xb7, 0x60, 0x50, + 0x22, 0xda, 0x52, 0xe6, 0xcc, 0xc2, 0x6f, 0xd2 + }; + + [Test ()] + public void TestRead () + { + // if we use larger size, StreamReader will read past newline and cause bad hash + var bytes = new byte[data.Length + 1]; + using (var ms = new MemoryStream (bytes)) { + using (var sw = new StreamWriter (ms)) { + // set NewLine to ensure we don't run into cross-platform issues on Windows + sw.NewLine = "\n"; + sw.WriteLine (data); + } + } + using (var ms = new MemoryStream (bytes)) { + using (var hs = new HashingStreamEx (ms, false, null)) { + using (var sr = new StreamReader (hs)) { + var read = sr.ReadLine (); + Assert.That (read, Is.EqualTo (data)); + } + // When the StreamReader is disposed, it calls Dispose on the + //HasingStreamEx, which computes the hash. + Assert.That (hs.Hash, Is.EqualTo (sha256HashOfData)); + } + } + } + + [Test ()] + public void TestWrite () + { + var bytes = new byte[16]; + using (var ms = new MemoryStream (bytes)) { + using (var hs = new HashingStreamEx (ms, true, null)) { + using (var sw = new StreamWriter (hs)) { + // set NewLine to ensure we don't run into cross-platform issues on Windows + sw.NewLine = "\n"; + sw.WriteLine (data); + } + // When the StreamWriter is disposed, it calls Dispose on the + //HasingStreamEx, which computes the hash. + Assert.That (hs.Hash, Is.EqualTo (sha256HashOfData)); + } + } + using (var ms = new MemoryStream (bytes)) { + using (var sr = new StreamReader (ms)) { + var read = sr.ReadLine (); + Assert.That (read, Is.EqualTo (data)); + } + } + } + } +} + diff --git a/KeePass2PCL.Test.Shared/Cryptography/HmacOtpTests.cs b/KeePass2PCL.Test.Shared/Cryptography/HmacOtpTests.cs new file mode 100644 index 0000000..ce3307b --- /dev/null +++ b/KeePass2PCL.Test.Shared/Cryptography/HmacOtpTests.cs @@ -0,0 +1,36 @@ +using NUnit.Framework; +using System; +using System.Text; + +#if KeePassLib +using KeePassLib.Cryptography; +#else +using KeePass2PCL.Cryptography; +#endif + +namespace KeePass2PCL.Test.Shared.Cryptography +{ + [TestFixture ()] + public class HmacOtpTests + { + // Using the test case from Appendix D of RFC 4226 + + const string secret = "12345678901234567890"; + static readonly string[] expectedHOTP = new string[] { + "755224", "287082", "359152", "969429", "338314", + "254676", "287922", "162583", "399871", "520489" + }; + + [Test ()] + public void TestGenerate () + { + var secretBytes = Encoding.UTF8.GetBytes (secret); + + for (ulong i = 0; i < 10; i++) { + var hotp = HmacOtp.Generate (secretBytes, i, 6, false, -1); + Assert.That (hotp, Is.EqualTo (expectedHOTP[i])); + } + } + } +} + diff --git a/KeePass2PCL.Test.Shared/KeePass2PCL.Test.Shared.projitems b/KeePass2PCL.Test.Shared/KeePass2PCL.Test.Shared.projitems new file mode 100644 index 0000000..fff96bf --- /dev/null +++ b/KeePass2PCL.Test.Shared/KeePass2PCL.Test.Shared.projitems @@ -0,0 +1,30 @@ + + + + $(MSBuildAllProjects);$(MSBuildThisFileFullPath) + true + {17F1C1A7-AE14-47AD-AE9A-ECFB9C45A559} + + + KeePass2PCL.Test.Shared + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/KeePass2PCL.Test.Shared/KeePass2PCL.Test.Shared.shproj b/KeePass2PCL.Test.Shared/KeePass2PCL.Test.Shared.shproj new file mode 100644 index 0000000..1f5f298 --- /dev/null +++ b/KeePass2PCL.Test.Shared/KeePass2PCL.Test.Shared.shproj @@ -0,0 +1,11 @@ + + + + {17F1C1A7-AE14-47AD-AE9A-ECFB9C45A559} + + + + + + + \ No newline at end of file diff --git a/KeePass2PCL.Test.Shared/Keys/CompositeKeyTests.cs b/KeePass2PCL.Test.Shared/Keys/CompositeKeyTests.cs new file mode 100644 index 0000000..e033962 --- /dev/null +++ b/KeePass2PCL.Test.Shared/Keys/CompositeKeyTests.cs @@ -0,0 +1,34 @@ +using NUnit.Framework; +using System; + +#if KeePassLib +using KeePassLib.Keys; +#else +using KeePass2PCL.Keys; +#endif + +namespace KeePass2PCL.Test.Shared.Keys +{ + [TestFixture ()] + public class CompositeKeyTests + { + [Test ()] + public void TestGenerateKey32 () + { + var originalKey = new byte[32]; + var expectedKey = new byte[32] { + 0xF0, 0xED, 0x57, 0xD5, 0xF0, 0xDA, 0xF3, 0x47, + 0x90, 0xD0, 0xDB, 0x43, 0x25, 0xC6, 0x81, 0x2C, + 0x81, 0x6A, 0x0D, 0x94, 0x96, 0xA9, 0x03, 0xE1, + 0x20, 0xD4, 0x3A, 0x3E, 0x45, 0xAD, 0x02, 0x65 + }; + const ulong rounds = 1; + + var composite = new CompositeKey (); + var key = composite.GenerateKey32 (originalKey, rounds); + Assert.That (key, Is.Not.Null); + var keyData = key.ReadData (); + Assert.That (keyData, Is.EqualTo (expectedKey)); + } + } +} diff --git a/KeePass2PCL.Test.Shared/Keys/KcpCustomKeyTests.cs b/KeePass2PCL.Test.Shared/Keys/KcpCustomKeyTests.cs new file mode 100644 index 0000000..597f051 --- /dev/null +++ b/KeePass2PCL.Test.Shared/Keys/KcpCustomKeyTests.cs @@ -0,0 +1,39 @@ +using NUnit.Framework; +using System; + +#if KeePassLib +using KeePassLib.Keys; +#else +using KeePass2PCL.Keys; +#endif + +namespace KeePass2PCL.Test.Shared.Keys +{ + [TestFixture ()] + public class KcpCustomKeyTests + { + static readonly byte[] testData = { + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 + }; + + [Test ()] + public void TestConstruct () + { + var expectedHash = new byte[32] { + 0xAF, 0x55, 0x70, 0xF5, 0xA1, 0x81, 0x0B, 0x7A, + 0xF7, 0x8C, 0xAF, 0x4B, 0xC7, 0x0A, 0x66, 0x0F, + 0x0D, 0xF5, 0x1E, 0x42, 0xBA, 0xF9, 0x1D, 0x4D, + 0xE5, 0xB2, 0x32, 0x8D, 0xE0, 0xE8, 0x3D, 0xFC + }; + + var key = new KcpCustomKey ("test1", testData, false); + var keyData = key.KeyData.ReadData (); + Assert.That (keyData, Is.EqualTo (testData)); + + key = new KcpCustomKey ("test2", testData, true); + keyData = key.KeyData.ReadData (); + Assert.That (keyData, Is.EqualTo (expectedHash)); + } + } +} + diff --git a/KeePass2PCL.Test.Shared/Keys/KcpKeyFileTests.cs b/KeePass2PCL.Test.Shared/Keys/KcpKeyFileTests.cs new file mode 100644 index 0000000..8cc0871 --- /dev/null +++ b/KeePass2PCL.Test.Shared/Keys/KcpKeyFileTests.cs @@ -0,0 +1,76 @@ +using NUnit.Framework; +using System; +using System.IO; + +#if KeePassLib +using KeePassLib.Keys; +#else +using KeePass2PCL.Keys; +#endif + +namespace KeePass2PCL.Test.Shared.Keys +{ + [TestFixture ()] + public class KcpKeyFileTests + { + const string testCreateFile = "TestCreate.xml"; + const string testKey = "0123456789"; + + const string expectedFileStart = + "\r\n" + + "\r\n" + + "\t\r\n" + + "\t\t1.00\r\n" + + "\t\r\n" + + "\t\r\n" + + "\t\t"; + + const string expectedFileEnd = "\t\r\n" + + "\r\n"; + + [Test ()] + public void TestConstruct () + { + var expectedKeyData = new byte[32] { + 0xC1, 0xB1, 0x12, 0x77, 0x23, 0xB8, 0x99, 0xB8, + 0xB9, 0x3B, 0x1B, 0xFF, 0x6C, 0xBE, 0xA1, 0x5B, + 0x8B, 0x99, 0xAC, 0xBD, 0x99, 0x51, 0x85, 0x95, + 0x31, 0xAA, 0x14, 0x3D, 0x95, 0xBF, 0x63, 0xFF + }; + + var fullPath = Path.Combine(Path.GetTempPath(), testCreateFile); + using (var fs = new FileStream(fullPath, FileMode.Create)) { + using (var sw = new StreamWriter(fs)) { + sw.Write (expectedFileStart); + sw.Write (testKey); + sw.Write (expectedFileEnd); + } + } + + try { + var keyFile = new KcpKeyFile (fullPath); + var keyData = keyFile.KeyData.ReadData (); + Assert.That (keyData, Is.EqualTo (expectedKeyData)); + } finally { + File.Delete (fullPath); + } + } + + [Test ()] + public void TestCreate () + { + var fullPath = Path.Combine(Path.GetTempPath(), testCreateFile); + File.Create(fullPath).Close(); + KcpKeyFile.Create (fullPath, null); + try { + var fileContents = File.ReadAllText (fullPath); + Assert.That (fileContents.Length, Is.EqualTo (187)); + Assert.That (fileContents, Does.StartWith (expectedFileStart)); + Assert.That (fileContents, Does.EndWith (expectedFileEnd)); + } finally { + File.Delete (fullPath); + } + } + } +} + diff --git a/KeePass2PCL.Test.Shared/Keys/KcpPasswordTests.cs b/KeePass2PCL.Test.Shared/Keys/KcpPasswordTests.cs new file mode 100644 index 0000000..533b5a7 --- /dev/null +++ b/KeePass2PCL.Test.Shared/Keys/KcpPasswordTests.cs @@ -0,0 +1,33 @@ +using NUnit.Framework; +using System; + +#if KeePassLib +using KeePassLib.Keys; +#else +using KeePass2PCL.Keys; +#endif + +namespace KeePass2PCL.Test.Shared.Keys +{ + [TestFixture ()] + public class KcpPasswordTests + { + const string testPassword = "password"; + + [Test ()] + public void TestConstruct () + { + var expectedHash = new byte[32] { + 0x5E, 0x88, 0x48, 0x98, 0xDA, 0x28, 0x04, 0x71, + 0x51, 0xD0, 0xE5, 0x6F, 0x8D, 0xC6, 0x29, 0x27, + 0x73, 0x60, 0x3D, 0x0D, 0x6A, 0xAB, 0xBD, 0xD6, + 0x2A, 0x11, 0xEF, 0x72, 0x1D, 0x15, 0x42, 0xD8 + }; + + var key = new KcpPassword (testPassword); + var keyData = key.KeyData.ReadData (); + Assert.That (keyData, Is.EqualTo (expectedHash)); + } + } +} + diff --git a/KeePass2PCL.Test.Shared/MyClass.cs b/KeePass2PCL.Test.Shared/MyClass.cs new file mode 100644 index 0000000..f57acff --- /dev/null +++ b/KeePass2PCL.Test.Shared/MyClass.cs @@ -0,0 +1,12 @@ +using System; + +namespace KeePass2PCL.Test.Shared +{ + public class MyClass + { + public MyClass () + { + } + } +} + diff --git a/KeePass2PCL.Test.Shared/Serialization/HashedBlockStreamTests.cs b/KeePass2PCL.Test.Shared/Serialization/HashedBlockStreamTests.cs new file mode 100644 index 0000000..b76122c --- /dev/null +++ b/KeePass2PCL.Test.Shared/Serialization/HashedBlockStreamTests.cs @@ -0,0 +1,71 @@ +using NUnit.Framework; +using System; +using System.IO; + +#if KeePassLib +using KeePassLib.Serialization; +#else +using KeePass2PCL.Serialization; +#endif + +namespace KeePass2PCL.Test.Shared.Serialization +{ + [TestFixture ()] + public class HashedBlockStreamTests + { + static readonly byte[] data = new byte[16]; + + static readonly byte[] hashStreamData = new byte[] { + // The first 4 bytes are an integer indicating the block index + 0x00, 0x00, 0x00, 0x00, + // Then the SHA-256 hash of the data + 0x37, 0x47, 0x08, 0xFF, 0xF7, 0x71, 0x9D, 0xD5, + 0x97, 0x9E, 0xC8, 0x75, 0xD5, 0x6C, 0xD2, 0x28, + 0x6F, 0x6D, 0x3C, 0xF7, 0xEC, 0x31, 0x7A, 0x3B, + 0x25, 0x63, 0x2A, 0xAB, 0x28, 0xEC, 0x37, 0xBB, + // then an integer that is the length of the data + 0x10, 0x00, 0x00, 0x00, + // and finally the data itself + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Next, a terminating block + 0x01, 0x00, 0x00, 0x00, + // terminating block is indicated by a hash of all 0s... + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // ...and by a size of 0 + 0x00, 0x00, 0x00, 0x00 + }; + + [Test ()] + public void TestRead () + { + using (var ms = new MemoryStream (hashStreamData)) { + using (var hbs = new HashedBlockStream (ms, false)) { + using (var br = new BinaryReader(hbs)) { + var bytes = br.ReadBytes (data.Length); + Assert.That (bytes, Is.EqualTo (data)); + Assert.That (() => br.ReadByte (), Throws.InstanceOf ()); + } + } + } + } + + [Test ()] + public void TestWrite () + { + var buffer = new byte[hashStreamData.Length]; + using (var ms = new MemoryStream (buffer)) { + using (var hbs = new HashedBlockStream (ms, true)) { + using (var bw = new BinaryWriter(hbs)) { + bw.Write (data); + } + } + Assert.That (buffer, Is.EqualTo (hashStreamData)); + } + } + } +} + diff --git a/KeePass2PCL.Test.Shared/Serialization/KdbxFileTests.cs b/KeePass2PCL.Test.Shared/Serialization/KdbxFileTests.cs new file mode 100644 index 0000000..47cbc5e --- /dev/null +++ b/KeePass2PCL.Test.Shared/Serialization/KdbxFileTests.cs @@ -0,0 +1,181 @@ +using NUnit.Framework; +using System; +using System.Drawing; +using System.IO; +using System.Text; +using System.Text.RegularExpressions; + + +#if KeePassLib +using KeePassLib; +using KeePassLib.Keys; +using KeePassLib.Security; +using KeePassLib.Serialization; +using KeePassLib.Collections; +#else +using KeePass2PCL.Keys; +using KeePass2PCL.Security; +using KeePass2PCL.Serialization; +using KeePass2PCL.Collections; +#endif + +namespace KeePass2PCL.Test.Shared.Serialization +{ + [TestFixture()] + public class KdbxFileTests + { + const string testLocalizedAppName = "My Localized App Name"; + + const string testDatabaseName = "My Database Name"; + const string testDatabaseDescription = "My Database Description"; + const string testDefaultUserName = "My Default User Name"; + const string testColor = "#FF0000"; // Red + + const string testRootGroupName = "My Root Group Name"; + const string testRootGroupNotes = "My Root Group Notes"; + const string testRootGroupDefaultAutoTypeSequence = "My Root Group Default Auto Type Sequence"; + + const string testDatabase = "\r\n" + + "\r\n" + + "\t\r\n" + + "\t\t" + testLocalizedAppName + "\r\n" + + "\t\t" + testDatabaseName + "\r\n" + + "\t\t2015-03-14T03:15:26Z\r\n" + + "\t\t" + testDatabaseDescription + "\r\n" + + "\t\t2015-03-14T03:15:26Z\r\n" + + "\t\t" + testDefaultUserName + "\r\n" + + "\t\t2015-03-14T03:15:26Z\r\n" + + "\t\t365\r\n" + + "\t\t" + testColor + "\r\n" + + "\t\t2015-03-14T03:15:26Z\r\n" + + "\t\t-1\r\n" + + "\t\t-1\r\n" + + "\t\t\r\n" + + "\t\t\tFalse\r\n" + + "\t\t\tFalse\r\n" + + "\t\t\tTrue\r\n" + + "\t\t\tFalse\r\n" + + "\t\t\tFalse\r\n" + + "\t\t\r\n" + + "\t\tTrue\r\n" + + "\t\tAAAAAAAAAAAAAAAAAAAAAA==\r\n" + + "\t\t2015-03-14T03:15:26Z\r\n" + + "\t\tAAAAAAAAAAAAAAAAAAAAAA==\r\n" + + "\t\t2015-03-14T03:15:26Z\r\n" + + "\t\t10\r\n" + + "\t\t6291456\r\n" + + "\t\tAAAAAAAAAAAAAAAAAAAAAA==\r\n" + + "\t\tAAAAAAAAAAAAAAAAAAAAAA==\r\n" + + "\t\t\r\n" + + "\t\t\r\n" + + "\t\r\n" + + "\t\r\n" + + "\t\t\r\n" + + "\t\t\tAAAAAAAAAAAAAAAAAAAAAA==\r\n" + + "\t\t\t" + testRootGroupName + "\r\n" + + "\t\t\t" + testRootGroupNotes + "\r\n" + + "\t\t\t49\r\n" + + "\t\t\t\r\n" + + "\t\t\t\t2015-03-14T03:15:26Z\r\n" + + "\t\t\t\t2015-03-14T03:15:26Z\r\n" + + "\t\t\t\t2015-03-14T03:15:26Z\r\n" + + "\t\t\t\t2015-03-14T03:15:26Z\r\n" + + "\t\t\t\tFalse\r\n" + + "\t\t\t\t0\r\n" + + "\t\t\t\t2015-03-14T03:15:26Z\r\n" + + "\t\t\t\r\n" + + "\t\t\tTrue\r\n" + + "\t\t\t" + testRootGroupDefaultAutoTypeSequence + "\r\n" + + "\t\t\tnull\r\n" + + "\t\t\tnull\r\n" + + "\t\t\tAAAAAAAAAAAAAAAAAAAAAA==\r\n" + + "\t\t\r\n" + + "\t\t\r\n" + + "\t\r\n" + + ""; + + const string testDate = "2015-03-14T03:15:26Z"; + + [Test()] + public void TestLoad() + { + var database = new PwDatabase(); + using (var ms = new MemoryStream(Encoding.UTF8.GetBytes(testDatabase))) + { + var file = new KdbxFile(database); + file.Load(ms, KdbxFormat.PlainXml, null); + } + Assert.That(database.Color.ToArgb(), Is.EqualTo(Color.Red.ToArgb())); + Assert.That(database.Compression, Is.EqualTo(PwCompressionAlgorithm.GZip)); + //Assert.That (database.CustomData, Is.EqualTo ()); + Assert.That(database.CustomIcons, Is.Empty); + } + + [Test()] + public void TestSave() + { + var buffer = new byte[4096]; + using (var ms = new MemoryStream(buffer)) + { + var database = new PwDatabase(); + database.New(new IOConnectionInfo(), new CompositeKey()); + var date = DateTime.Parse(testDate); + PwDatabase.LocalizedAppName = testLocalizedAppName; + database.Name = testDatabaseName; + database.NameChanged = date; + database.Description = testDatabaseDescription; + database.DescriptionChanged = date; + database.DefaultUserName = testDefaultUserName; + database.DefaultUserNameChanged = date; + database.Color = Color.Red; + database.MasterKeyChanged = date; + database.RecycleBinChanged = date; + database.EntryTemplatesGroupChanged = date; + database.RootGroup.Uuid = PwUuid.Zero; + database.RootGroup.Name = testRootGroupName; + database.RootGroup.Notes = testRootGroupNotes; + database.RootGroup.DefaultAutoTypeSequence = testRootGroupDefaultAutoTypeSequence; + database.RootGroup.CreationTime = date; + database.RootGroup.LastModificationTime = date; + database.RootGroup.LastAccessTime = date; + database.RootGroup.ExpiryTime = date; + database.RootGroup.LocationChanged = date; + var file = new KdbxFile(database); + file.Save(ms, null, KdbxFormat.PlainXml, null); + } + var fileContents = Encoding.UTF8.GetString(buffer).Replace("\0", ""); + if (typeof(KdbxFile).Namespace.StartsWith("KeePassLib.") + && Environment.OSVersion.Platform != PlatformID.Win32NT) + { + // Upstream KeePassLib does not specify line endings for XmlTextWriter, + // so it uses native line endings. + fileContents = fileContents.Replace("\n", "\r\n"); + } + Assert.That(fileContents, Is.EqualTo(testDatabase)); + } + + [Test] + public void TestSearch() + { + var database = new PwDatabase(); + using (var ms = new MemoryStream(Encoding.UTF8.GetBytes(testDatabase))) + { + var file = new KdbxFile(database); + file.Load(ms, KdbxFormat.PlainXml, null); + } + var sp = new SearchParameters() + { + SearchString = "sfsoiwsefsi" + }; + var listStorage = new PwObjectList(); + database.RootGroup.SearchEntries(sp, listStorage); + Assert.AreEqual(0U, listStorage.UCount); + var entry = new PwEntry(true, true); + entry.Strings.Set("Title", new ProtectedString(false, "NaMe")); + database.RootGroup.AddEntry(entry, true); + sp.SearchString = "name"; + database.RootGroup.SearchEntries(sp, listStorage); + Assert.AreEqual(1U, listStorage.UCount); + } + } +} diff --git a/KeePass2PCL.Test.Shared/Utility/GfxUtilTests.cs b/KeePass2PCL.Test.Shared/Utility/GfxUtilTests.cs new file mode 100644 index 0000000..ce25156 --- /dev/null +++ b/KeePass2PCL.Test.Shared/Utility/GfxUtilTests.cs @@ -0,0 +1,32 @@ +using NUnit.Framework; +using System; + +#if KeePassLib +using KeePassLib.Utility; +#else +using Splat; +using KeePass2PCL.Utility; +#endif + +namespace KeePass2PCL.Test.Shared.Utility +{ + [TestFixture ()] + public class GfxUtilTests + { + // 16x16 all white PNG file, base64 encoded + const string testImageData = + "iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAIAAACQkWg2AAAACXBIWXMAAAsTAAA" + + "LEwEAmpwYAAAAB3RJTUUH3wMOFgIgmTCUMQAAABl0RVh0Q29tbWVudABDcmVhdG" + + "VkIHdpdGggR0lNUFeBDhcAAAAaSURBVCjPY/z//z8DKYCJgUQwqmFUw9DRAABVb" + + "QMdny4VogAAAABJRU5ErkJggg=="; + + [Test ()] + public void TestLoadImage () + { + var testData = Convert.FromBase64String (testImageData); + var image = GfxUtil.LoadImage (testData); + Assert.That (image.Width, Is.EqualTo (16)); + Assert.That (image.Height, Is.EqualTo (16)); + } + } +} diff --git a/KeePass2PCL.Test.UWP/Assets/LockScreenLogo.scale-200.png b/KeePass2PCL.Test.UWP/Assets/LockScreenLogo.scale-200.png new file mode 100644 index 0000000..735f57a Binary files /dev/null and b/KeePass2PCL.Test.UWP/Assets/LockScreenLogo.scale-200.png differ diff --git a/KeePass2PCL.Test.UWP/Assets/SplashScreen.scale-200.png b/KeePass2PCL.Test.UWP/Assets/SplashScreen.scale-200.png new file mode 100644 index 0000000..023e7f1 Binary files /dev/null and b/KeePass2PCL.Test.UWP/Assets/SplashScreen.scale-200.png differ diff --git a/KeePass2PCL.Test.UWP/Assets/Square150x150Logo.scale-200.png b/KeePass2PCL.Test.UWP/Assets/Square150x150Logo.scale-200.png new file mode 100644 index 0000000..af49fec Binary files /dev/null and b/KeePass2PCL.Test.UWP/Assets/Square150x150Logo.scale-200.png differ diff --git a/KeePass2PCL.Test.UWP/Assets/Square44x44Logo.scale-200.png b/KeePass2PCL.Test.UWP/Assets/Square44x44Logo.scale-200.png new file mode 100644 index 0000000..ce342a2 Binary files /dev/null and b/KeePass2PCL.Test.UWP/Assets/Square44x44Logo.scale-200.png differ diff --git a/KeePass2PCL.Test.UWP/Assets/Square44x44Logo.targetsize-24_altform-unplated.png b/KeePass2PCL.Test.UWP/Assets/Square44x44Logo.targetsize-24_altform-unplated.png new file mode 100644 index 0000000..f6c02ce Binary files /dev/null and b/KeePass2PCL.Test.UWP/Assets/Square44x44Logo.targetsize-24_altform-unplated.png differ diff --git a/KeePass2PCL.Test.UWP/Assets/StoreLogo.png b/KeePass2PCL.Test.UWP/Assets/StoreLogo.png new file mode 100644 index 0000000..7385b56 Binary files /dev/null and b/KeePass2PCL.Test.UWP/Assets/StoreLogo.png differ diff --git a/KeePass2PCL.Test.UWP/Assets/Wide310x150Logo.scale-200.png b/KeePass2PCL.Test.UWP/Assets/Wide310x150Logo.scale-200.png new file mode 100644 index 0000000..288995b Binary files /dev/null and b/KeePass2PCL.Test.UWP/Assets/Wide310x150Logo.scale-200.png differ diff --git a/KeePass2PCL.Test.UWP/KeePass2PCL.Test.UWP.csproj b/KeePass2PCL.Test.UWP/KeePass2PCL.Test.UWP.csproj new file mode 100644 index 0000000..d11dd36 --- /dev/null +++ b/KeePass2PCL.Test.UWP/KeePass2PCL.Test.UWP.csproj @@ -0,0 +1,172 @@ + + + + + Debug + x86 + {4E21AE3C-13FF-4773-824C-D51542AD1A7B} + AppContainerExe + Properties + KeePass2PCL.Test.UWP + KeePass2PCL.Test.UWP + en-US + UAP + 10.0.15063.0 + 10.0.10240.0 + 14 + 512 + {A5A43C5B-DE2A-4C0C-9213-0A381AF9435A};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} + KeePass2PCL.Test.UWP_TemporaryKey.pfx + $(VisualStudioVersion) + + + true + bin\x86\Debug\ + DEBUG;TRACE;NETFX_CORE;WINDOWS_UWP + ;2008 + full + x86 + false + prompt + true + + + bin\x86\Release\ + TRACE;NETFX_CORE;WINDOWS_UWP + true + ;2008 + pdbonly + x86 + false + prompt + true + true + + + true + bin\ARM\Debug\ + DEBUG;TRACE;NETFX_CORE;WINDOWS_UWP + ;2008 + full + ARM + false + prompt + true + + + bin\ARM\Release\ + TRACE;NETFX_CORE;WINDOWS_UWP + true + ;2008 + pdbonly + ARM + false + prompt + true + true + + + true + bin\x64\Debug\ + DEBUG;TRACE;NETFX_CORE;WINDOWS_UWP + ;2008 + full + x64 + false + prompt + true + + + bin\x64\Release\ + TRACE;NETFX_CORE;WINDOWS_UWP + true + ;2008 + pdbonly + x64 + false + prompt + true + true + + + PackageReference + + + + + + + + + UnitTestApp.xaml + + + + + MSBuild:Compile + Designer + + + + + Designer + + + + + + + + + + + + + + + + + + + 5.4.0 + + + 1.1.18 + + + 1.1.18 + + + 2.0.147 + + + 1.1.0 + + + 1.0.2 + + + 2.0.0 + + + + + {2e710089-9559-4967-846c-e763dd1f3acb} + KeePass2PCL + + + + + + + 14.0 + + + + \ No newline at end of file diff --git a/KeePass2PCL.Test.UWP/KeePass2PCL.Test.UWP_TemporaryKey.pfx b/KeePass2PCL.Test.UWP/KeePass2PCL.Test.UWP_TemporaryKey.pfx new file mode 100644 index 0000000..f04aea4 Binary files /dev/null and b/KeePass2PCL.Test.UWP/KeePass2PCL.Test.UWP_TemporaryKey.pfx differ diff --git a/KeePass2PCL.Test.UWP/Package.appxmanifest b/KeePass2PCL.Test.UWP/Package.appxmanifest new file mode 100644 index 0000000..a869c8e --- /dev/null +++ b/KeePass2PCL.Test.UWP/Package.appxmanifest @@ -0,0 +1,45 @@ + + + + + + + + + KeePass2PCL.Test.UWP + anpan + Assets\StoreLogo.png + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/KeePass2PCL.Test.UWP/Properties/AssemblyInfo.cs b/KeePass2PCL.Test.UWP/Properties/AssemblyInfo.cs new file mode 100644 index 0000000..175ba33 --- /dev/null +++ b/KeePass2PCL.Test.UWP/Properties/AssemblyInfo.cs @@ -0,0 +1,18 @@ +using System.Reflection; +using System.Runtime.CompilerServices; +using System.Runtime.InteropServices; + +[assembly: AssemblyTitle("KeePass2PCL.Test.UWP")] +[assembly: AssemblyDescription("")] +[assembly: AssemblyConfiguration("")] +[assembly: AssemblyCompany("")] +[assembly: AssemblyProduct("KeePass2PCL.Test.UWP")] +[assembly: AssemblyCopyright("Copyright © 2017")] +[assembly: AssemblyTrademark("")] +[assembly: AssemblyCulture("")] +[assembly: AssemblyMetadata("TargetPlatform","UAP")] + +// [assembly: AssemblyVersion("1.0.*")] +[assembly: AssemblyVersion("1.0.0.0")] +[assembly: AssemblyFileVersion("1.0.0.0")] +[assembly: ComVisible(false)] \ No newline at end of file diff --git a/KeePass2PCL.Test.UWP/Properties/UnitTestApp.rd.xml b/KeePass2PCL.Test.UWP/Properties/UnitTestApp.rd.xml new file mode 100644 index 0000000..efee59d --- /dev/null +++ b/KeePass2PCL.Test.UWP/Properties/UnitTestApp.rd.xml @@ -0,0 +1,29 @@ + + + + + + + + + + + \ No newline at end of file diff --git a/KeePass2PCL.Test.UWP/PwDatabaseTests.cs b/KeePass2PCL.Test.UWP/PwDatabaseTests.cs new file mode 100644 index 0000000..868aa95 --- /dev/null +++ b/KeePass2PCL.Test.UWP/PwDatabaseTests.cs @@ -0,0 +1,117 @@ +using System.Reflection; +using Microsoft.VisualStudio.TestTools.UnitTesting; +using PCLStorage; +using System.IO; +using KeePass2PCL.Serialization; +using KeePass2PCL.Keys; + +namespace KeePass2PCL.Test.UWP +{ + [TestClass] + public class PwDatabaseTests + { + [TestMethod] + public void Open_With_Wrong_Password_Test() + { + IFolder folder = SpecialFolder.Current.Local; + IFolder testData = folder.CreateFolderAsync("TestData", + CreationCollisionOption.OpenIfExists).Result; + IFile file = testData.CreateFileAsync("1.kdbx", + CreationCollisionOption.ReplaceExisting).Result; + var fileStream = file.OpenAsync(PCLStorage.FileAccess.ReadAndWrite).Result; + var assembly = typeof(PwDatabaseTests).GetTypeInfo().Assembly; + var stream = assembly.GetManifestResourceStream( + "KeePass2PCL.Test.UWP.TestData.1.kdbx"); + using (var reader = new BinaryReader(stream)) + using (var fileWriter = new BinaryWriter(fileStream)) + { + fileWriter.Write(reader.ReadBytes((int)stream.Length)); + } + + var ci = new IOConnectionInfo(); + ci.Path = file.Path; + var key = new CompositeKey(); + key.AddUserKey(new KcpPassword("0")); + var db = new PwDatabase(); + bool wasException = false; + try + { + db.Open(ci, key, null); + } + catch (InvalidCompositeKeyException) + { + wasException = true; + } + Assert.IsTrue(wasException); + file.DeleteAsync().Wait(); + testData.DeleteAsync().Wait(); + } + + [TestMethod] + public void Open_With_KeyFile_Test() + { + IFolder folder = SpecialFolder.Current.Local; + IFolder testData = folder.CreateFolderAsync("TestData", + CreationCollisionOption.OpenIfExists).Result; + IFile keyFile = testData.CreateFileAsync("1.key", + CreationCollisionOption.ReplaceExisting).Result; + var fileStream = keyFile.OpenAsync(PCLStorage.FileAccess.ReadAndWrite).Result; + var assembly = typeof(PwDatabaseTests).GetTypeInfo().Assembly; + var stream = assembly.GetManifestResourceStream( + "KeePass2PCL.Test.UWP.TestData.1.key"); + using (var reader = new BinaryReader(stream)) + using (var fileWriter = new BinaryWriter(fileStream)) + { + fileWriter.Write(reader.ReadBytes((int)stream.Length)); + } + + IFile file = testData.CreateFileAsync("1key.kdbx", + CreationCollisionOption.ReplaceExisting).Result; + fileStream = file.OpenAsync(PCLStorage.FileAccess.ReadAndWrite).Result; + assembly = typeof(PwDatabaseTests).GetTypeInfo().Assembly; + stream = assembly.GetManifestResourceStream( + "KeePass2PCL.Test.UWP.TestData.1key.kdbx"); + using (var reader = new BinaryReader(stream)) + using (var fileWriter = new BinaryWriter(fileStream)) + { + fileWriter.Write(reader.ReadBytes((int)stream.Length)); + } + + var ci = new IOConnectionInfo(); + ci.Path = file.Path; + var key = new CompositeKey(); + key.AddUserKey(new KcpKeyFile(keyFile.Path)); + var db = new PwDatabase(); + db.Open(ci, key, null); + keyFile.DeleteAsync().Wait(); + file.DeleteAsync().Wait(); + testData.DeleteAsync().Wait(); + } + + [TestMethod] + public void New_Test() + { + IFolder folder = SpecialFolder.Current.Local; + IFolder testData = folder.CreateFolderAsync("TestData", + CreationCollisionOption.OpenIfExists).Result; + IFile file = testData.CreateFileAsync("1.kdbx", + CreationCollisionOption.ReplaceExisting).Result; + + var ci = new IOConnectionInfo(); + ci.Path = file.Path; + var key = new CompositeKey(); + key.AddUserKey(new KcpPassword("0")); + var db = new PwDatabase(); + db.New(ci, key); + var initialEnitiesCount = db.RootGroup.GetEntriesCount(true); + Assert.AreNotEqual(0, initialEnitiesCount); + db.Save(null); + db.Close(); + Assert.IsNull(db.RootGroup); + db = new PwDatabase(); + db.Open(ci, key, null); + Assert.AreEqual(initialEnitiesCount, + db.RootGroup.GetEntriesCount(true)); + } + } +} diff --git a/KeePass2PCL.Test.UWP/TestData/1.kdbx b/KeePass2PCL.Test.UWP/TestData/1.kdbx new file mode 100644 index 0000000..9a6ea8a Binary files /dev/null and b/KeePass2PCL.Test.UWP/TestData/1.kdbx differ diff --git a/KeePass2PCL.Test.UWP/TestData/1.key b/KeePass2PCL.Test.UWP/TestData/1.key new file mode 100644 index 0000000..fcbc781 --- /dev/null +++ b/KeePass2PCL.Test.UWP/TestData/1.key @@ -0,0 +1,9 @@ + + + + 1.00 + + + M+5k7gXYzjN8Vwp5akdSwaPeUhBq0bC0q5qnSYlJmAw= + + diff --git a/KeePass2PCL.Test.UWP/TestData/1key.kdbx b/KeePass2PCL.Test.UWP/TestData/1key.kdbx new file mode 100644 index 0000000..838ad6c Binary files /dev/null and b/KeePass2PCL.Test.UWP/TestData/1key.kdbx differ diff --git a/KeePass2PCL.Test.UWP/UnitTestApp.xaml b/KeePass2PCL.Test.UWP/UnitTestApp.xaml new file mode 100644 index 0000000..04a2d2b --- /dev/null +++ b/KeePass2PCL.Test.UWP/UnitTestApp.xaml @@ -0,0 +1,8 @@ + + + diff --git a/KeePass2PCL.Test.UWP/UnitTestApp.xaml.cs b/KeePass2PCL.Test.UWP/UnitTestApp.xaml.cs new file mode 100644 index 0000000..22ee43c --- /dev/null +++ b/KeePass2PCL.Test.UWP/UnitTestApp.xaml.cs @@ -0,0 +1,102 @@ +using System; +using System.Collections.Generic; +using System.IO; +using System.Linq; +using System.Runtime.InteropServices.WindowsRuntime; +using Windows.ApplicationModel; +using Windows.ApplicationModel.Activation; +using Windows.Foundation; +using Windows.Foundation.Collections; +using Windows.UI.Xaml; +using Windows.UI.Xaml.Controls; +using Windows.UI.Xaml.Controls.Primitives; +using Windows.UI.Xaml.Data; +using Windows.UI.Xaml.Input; +using Windows.UI.Xaml.Media; +using Windows.UI.Xaml.Navigation; + +namespace KeePass2PCL.Test.UWP +{ + /// + /// Provides application-specific behavior to supplement the default Application class. + /// + sealed partial class App : Application + { + /// + /// Initializes the singleton application object. This is the first line of authored code + /// executed, and as such is the logical equivalent of main() or WinMain(). + /// + public App() + { + this.InitializeComponent(); + this.Suspending += OnSuspending; + } + + /// + /// Invoked when the application is launched normally by the end user. Other entry points + /// will be used such as when the application is launched to open a specific file. + /// + /// Details about the launch request and process. + protected override void OnLaunched(LaunchActivatedEventArgs e) + { + +#if DEBUG + if (System.Diagnostics.Debugger.IsAttached) + { + this.DebugSettings.EnableFrameRateCounter = true; + } +#endif + + Frame rootFrame = Window.Current.Content as Frame; + + // Do not repeat app initialization when the Window already has content, + // just ensure that the window is active + if (rootFrame == null) + { + // Create a Frame to act as the navigation context and navigate to the first page + rootFrame = new Frame(); + + rootFrame.NavigationFailed += OnNavigationFailed; + + if (e.PreviousExecutionState == ApplicationExecutionState.Terminated) + { + //TODO: Load state from previously suspended application + } + + // Place the frame in the current Window + Window.Current.Content = rootFrame; + } + + Microsoft.VisualStudio.TestPlatform.TestExecutor.UnitTestClient.CreateDefaultUI(); + + // Ensure the current window is active + Window.Current.Activate(); + + Microsoft.VisualStudio.TestPlatform.TestExecutor.UnitTestClient.Run(e.Arguments); + } + + /// + /// Invoked when Navigation to a certain page fails + /// + /// The Frame which failed navigation + /// Details about the navigation failure + void OnNavigationFailed(object sender, NavigationFailedEventArgs e) + { + throw new Exception("Failed to load Page " + e.SourcePageType.FullName); + } + + /// + /// Invoked when application execution is being suspended. Application state is saved + /// without knowing whether the application will be terminated or resumed with the contents + /// of memory still intact. + /// + /// The source of the suspend request. + /// Details about the suspend request. + private void OnSuspending(object sender, SuspendingEventArgs e) + { + var deferral = e.SuspendingOperation.GetDeferral(); + //TODO: Save application state and stop any background activity + deferral.Complete(); + } + } +} diff --git a/KeePass2PCL.Test/KeePass2PCL.Test.KeePassLib.csproj b/KeePass2PCL.Test/KeePass2PCL.Test.KeePassLib.csproj new file mode 100644 index 0000000..a40e2e8 --- /dev/null +++ b/KeePass2PCL.Test/KeePass2PCL.Test.KeePassLib.csproj @@ -0,0 +1,65 @@ + + + + + Debug + AnyCPU + {2637FAA9-838C-43AB-81F3-BB231E0E1DCA} + Library + KeePass2PCL.Test.KeePassLib + KeePass2PCL.Test.KeePassLib + v4.5 + + + + + true + full + false + bin\Debug + DEBUG;KeePassLib + prompt + 4 + false + + + true + bin\Release + KeePassLib; + prompt + 4 + false + + + + ..\packages\Castle.Core.4.1.1\lib\net45\Castle.Core.dll + + + ..\packages\pt.KeePassLib.2.35.2\lib\net20\KeePassLib.dll + + + ..\packages\Moq.4.7.99\lib\net45\Moq.dll + + + ..\packages\NUnit.3.7.1\lib\net45\nunit.framework.dll + + + + + + + + + + + + + + + + + This project references NuGet package(s) that are missing on this computer. Use NuGet Package Restore to download them. For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}. + + + + \ No newline at end of file diff --git a/KeePass2PCL.Test/app.config b/KeePass2PCL.Test/app.config new file mode 100644 index 0000000..81b66be --- /dev/null +++ b/KeePass2PCL.Test/app.config @@ -0,0 +1,11 @@ + + + + + + + + + + + \ No newline at end of file diff --git a/KeePass2PCL.Test/packages.config b/KeePass2PCL.Test/packages.config new file mode 100644 index 0000000..58f1691 --- /dev/null +++ b/KeePass2PCL.Test/packages.config @@ -0,0 +1,8 @@ + + + + + + + + \ No newline at end of file diff --git a/ModernKeePass.sln b/ModernKeePass.sln index 4c7e596..afc08f4 100644 --- a/ModernKeePass.sln +++ b/ModernKeePass.sln @@ -7,6 +7,8 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "ModernKeePass", "ModernKeeP EndProject Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "ModernKeePassLibPCL", "ModernKeePassLib\ModernKeePassLibPCL.csproj", "{2E710089-9559-4967-846C-E763DD1F3ACB}" EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "ModernKeePassLib.Test", "ModernKeePassLib.Test\ModernKeePassLib.Test.csproj", "{067456C0-086C-46A8-B37F-1405717B7BFC}" +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|Any CPU = Debug|Any CPU @@ -59,6 +61,22 @@ Global {2E710089-9559-4967-846C-E763DD1F3ACB}.Release|x64.Build.0 = Release|Any CPU {2E710089-9559-4967-846C-E763DD1F3ACB}.Release|x86.ActiveCfg = Release|Any CPU {2E710089-9559-4967-846C-E763DD1F3ACB}.Release|x86.Build.0 = Release|Any CPU + {067456C0-086C-46A8-B37F-1405717B7BFC}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {067456C0-086C-46A8-B37F-1405717B7BFC}.Debug|Any CPU.Build.0 = Debug|Any CPU + {067456C0-086C-46A8-B37F-1405717B7BFC}.Debug|ARM.ActiveCfg = Debug|Any CPU + {067456C0-086C-46A8-B37F-1405717B7BFC}.Debug|ARM.Build.0 = Debug|Any CPU + {067456C0-086C-46A8-B37F-1405717B7BFC}.Debug|x64.ActiveCfg = Debug|Any CPU + {067456C0-086C-46A8-B37F-1405717B7BFC}.Debug|x64.Build.0 = Debug|Any CPU + {067456C0-086C-46A8-B37F-1405717B7BFC}.Debug|x86.ActiveCfg = Debug|Any CPU + {067456C0-086C-46A8-B37F-1405717B7BFC}.Debug|x86.Build.0 = Debug|Any CPU + {067456C0-086C-46A8-B37F-1405717B7BFC}.Release|Any CPU.ActiveCfg = Release|Any CPU + {067456C0-086C-46A8-B37F-1405717B7BFC}.Release|Any CPU.Build.0 = Release|Any CPU + {067456C0-086C-46A8-B37F-1405717B7BFC}.Release|ARM.ActiveCfg = Release|Any CPU + {067456C0-086C-46A8-B37F-1405717B7BFC}.Release|ARM.Build.0 = Release|Any CPU + {067456C0-086C-46A8-B37F-1405717B7BFC}.Release|x64.ActiveCfg = Release|Any CPU + {067456C0-086C-46A8-B37F-1405717B7BFC}.Release|x64.Build.0 = Release|Any CPU + {067456C0-086C-46A8-B37F-1405717B7BFC}.Release|x86.ActiveCfg = Release|Any CPU + {067456C0-086C-46A8-B37F-1405717B7BFC}.Release|x86.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE diff --git a/ModernKeePass/Common/DatabaseHelper.cs b/ModernKeePass/Common/DatabaseHelper.cs index d0e2ed5..4306b92 100644 --- a/ModernKeePass/Common/DatabaseHelper.cs +++ b/ModernKeePass/Common/DatabaseHelper.cs @@ -31,8 +31,11 @@ namespace ModernKeePass.Common _pwDatabase.Open(IOConnectionInfo.FromFile(databaseFile), key, new NullStatusLogger()); //_pwDatabase.Open(IOConnectionInfo.FromPath(databaseFile.Path), key, new NullStatusLogger()); IsOpen = _pwDatabase.IsOpen; - Name = databaseFile.DisplayName; - RootGroup = new GroupVm(_pwDatabase.RootGroup); + if (IsOpen) + { + Name = databaseFile.DisplayName; + RootGroup = new GroupVm(_pwDatabase.RootGroup); + } } catch (ArgumentNullException) { diff --git a/ModernKeePass/MainPage.xaml b/ModernKeePass/MainPage.xaml index 3ecfd71..b0a737e 100644 --- a/ModernKeePass/MainPage.xaml +++ b/ModernKeePass/MainPage.xaml @@ -20,7 +20,7 @@ - + @@ -37,6 +37,7 @@ New File Recent files - Coming soon + Url files - Coming soon @@ -56,6 +57,6 @@