Update to KeePassLib version 2.45

This commit is contained in:
Geoffroy BONNEVILLE
2020-05-12 12:46:25 +02:00
parent 107e009807
commit 2e1cc97738
21 changed files with 166 additions and 65 deletions

View File

@@ -282,7 +282,6 @@ namespace ModernKeePassLib.Cryptography
{ {
byte[] pb = new byte[32]; byte[] pb = new byte[32];
try { m_rng.GetBytes(pb); } try { m_rng.GetBytes(pb); }
catch(Exception) catch(Exception)
{ {

View File

@@ -151,6 +151,8 @@ namespace ModernKeePassLib.Cryptography.KeyDerivation
aes.ProcessBlock(pbNewKey32, 0, pbNewKey32, 0); aes.ProcessBlock(pbNewKey32, 0, pbNewKey32, 0);
aes.ProcessBlock(pbNewKey32, 16, pbNewKey32, 16); aes.ProcessBlock(pbNewKey32, 16, pbNewKey32, 16);
} }
aes.Reset();
#else #else
byte[] pbIV = new byte[16]; byte[] pbIV = new byte[16];

View File

@@ -468,7 +468,6 @@ namespace ModernKeePassLib.Cryptography.KeyDerivation
#if ModernKeePassLib #if ModernKeePassLib
Task.Factory.StartNew(FillSegmentThr, ti); Task.Factory.StartNew(FillSegmentThr, ti);
//ThreadPool.RunAsync(a => FillSegmentThr(ti));
#else #else
if(!ThreadPool.QueueUserWorkItem(FillSegmentThr, ti)) if(!ThreadPool.QueueUserWorkItem(FillSegmentThr, ti))
{ {

View File

@@ -282,6 +282,7 @@ namespace ModernKeePassLib.Keys
return GenerateKey32(p); return GenerateKey32(p);
#else #else
if(sl == null) return GenerateKey32(p); if(sl == null) return GenerateKey32(p);
CkGkTaskInfo ti = new CkGkTaskInfo(); CkGkTaskInfo ti = new CkGkTaskInfo();
ThreadStart f = delegate() ThreadStart f = delegate()

View File

@@ -3,11 +3,11 @@
<PropertyGroup> <PropertyGroup>
<TargetFramework>netstandard1.2</TargetFramework> <TargetFramework>netstandard1.2</TargetFramework>
<Description>Portable KeePass Password Management Library that targets .Net Standard and WinRT. Allows reading, editing and writing to KeePass 2.x databases.</Description> <Description>Portable KeePass Password Management Library that targets .Net Standard and WinRT. Allows reading, editing and writing to KeePass 2.x databases.</Description>
<Version>2.44.3</Version> <Version>2.45.1</Version>
<Authors>Geoffroy Bonneville</Authors> <Authors>Geoffroy Bonneville</Authors>
<Company>wismna</Company> <Company>wismna</Company>
<PackageProjectUrl>https://github.com/wismna/ModernKeePass</PackageProjectUrl> <PackageProjectUrl>https://github.com/wismna/ModernKeePass</PackageProjectUrl>
<PackageReleaseNotes>Implementation of KeePass library version 2.44</PackageReleaseNotes> <PackageReleaseNotes>Implementation of KeePass library version 2.45</PackageReleaseNotes>
<Copyright>Copyright © 2018 Geoffroy Bonneville</Copyright> <Copyright>Copyright © 2018 Geoffroy Bonneville</Copyright>
<PackageTags>KeePass KeePassLib Portable PCL NetStandard</PackageTags> <PackageTags>KeePass KeePassLib Portable PCL NetStandard</PackageTags>
<PackageLicenseExpression></PackageLicenseExpression> <PackageLicenseExpression></PackageLicenseExpression>

View File

@@ -1,6 +1,6 @@
/* /*
KeePass Password Safe - The Open-Source Password Manager KeePass Password Safe - The Open-Source Password Manager
Copyright (C) 2003-2018 Dominik Reichl <dominik.reichl@t-online.de> Copyright (C) 2003-2020 Dominik Reichl <dominik.reichl@t-online.de>
This program is free software; you can redistribute it and/or modify This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by it under the terms of the GNU General Public License as published by
@@ -27,7 +27,7 @@ namespace ModernKeePassLib.Native
{ {
internal static class ClipboardU internal static class ClipboardU
{ {
private const string XSel = "xsel"; internal const string XSel = "xsel";
private const string XSelV = "--version"; private const string XSelV = "--version";
private const string XSelR = "--output --clipboard"; private const string XSelR = "--output --clipboard";
private const string XSelC = "--clear --clipboard"; private const string XSelC = "--clear --clipboard";

View File

@@ -19,6 +19,7 @@
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.ComponentModel;
using System.Diagnostics; using System.Diagnostics;
using System.Reflection; using System.Reflection;
using System.Runtime.InteropServices; using System.Runtime.InteropServices;
@@ -273,7 +274,13 @@ namespace ModernKeePassLib.Native
return strOutput; return strOutput;
} }
#if DEBUG #if DEBUG
catch(Exception ex) { Debug.Assert(ex is ThreadAbortException); } catch(ThreadAbortException) { }
catch(Win32Exception exW)
{
Debug.Assert((strAppPath == ClipboardU.XSel) &&
(exW.NativeErrorCode == 2)); // XSel not found
}
catch(Exception) { Debug.Assert(false); }
#else #else
catch(Exception) { } catch(Exception) { }
#endif #endif

View File

@@ -21,6 +21,7 @@ using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.ComponentModel; using System.ComponentModel;
using System.Diagnostics; using System.Diagnostics;
using System.Net;
using System.Xml.Serialization; using System.Xml.Serialization;
using ModernKeePassLib.Delegates; using ModernKeePassLib.Delegates;
@@ -55,18 +56,18 @@ namespace ModernKeePassLib
/// e.g. 2.19 = 0x02130000. /// e.g. 2.19 = 0x02130000.
/// It is highly recommended to use <c>FileVersion64</c> instead. /// It is highly recommended to use <c>FileVersion64</c> instead.
/// </summary> /// </summary>
public static readonly uint Version32 = 0x022C0000; public static readonly uint Version32 = 0x022D0000;
/// <summary> /// <summary>
/// Version, encoded as 64-bit unsigned integer /// Version, encoded as 64-bit unsigned integer
/// (component-wise, 16 bits per component). /// (component-wise, 16 bits per component).
/// </summary> /// </summary>
public static readonly ulong FileVersion64 = 0x0002002C00000000UL; public static readonly ulong FileVersion64 = 0x0002002D00000000UL;
/// <summary> /// <summary>
/// Version, encoded as string. /// Version, encoded as string.
/// </summary> /// </summary>
public static readonly string VersionString = "2.44"; public static readonly string VersionString = "2.45";
public static readonly string Copyright = @"Copyright © 2003-2020 Dominik Reichl"; public static readonly string Copyright = @"Copyright © 2003-2020 Dominik Reichl";
@@ -187,6 +188,8 @@ namespace ModernKeePassLib
/// </summary> /// </summary>
internal const int UIUpdateDelay = 50; internal const int UIUpdateDelay = 50;
internal const uint QualityBitsWeak = 79;
/// <summary> /// <summary>
/// Check if a name is a standard field name. /// Check if a name is a standard field name.
/// </summary> /// </summary>
@@ -507,13 +510,13 @@ namespace ModernKeePassLib
public sealed class ObjectTouchedEventArgs : EventArgs public sealed class ObjectTouchedEventArgs : EventArgs
{ {
private object m_o; private readonly object m_o;
public object Object { get { return m_o; } } public object Object { get { return m_o; } }
private bool m_bModified; private readonly bool m_bModified;
public bool Modified { get { return m_bModified; } } public bool Modified { get { return m_bModified; } }
private bool m_bParentsTouched; private readonly bool m_bParentsTouched;
public bool ParentsTouched { get { return m_bParentsTouched; } } public bool ParentsTouched { get { return m_bParentsTouched; } }
public ObjectTouchedEventArgs(object o, bool bModified, public ObjectTouchedEventArgs(object o, bool bModified,
@@ -527,13 +530,13 @@ namespace ModernKeePassLib
public sealed class IOAccessEventArgs : EventArgs public sealed class IOAccessEventArgs : EventArgs
{ {
private IOConnectionInfo m_ioc; private readonly IOConnectionInfo m_ioc;
public IOConnectionInfo IOConnectionInfo { get { return m_ioc; } } public IOConnectionInfo IOConnectionInfo { get { return m_ioc; } }
private IOConnectionInfo m_ioc2; private readonly IOConnectionInfo m_ioc2;
public IOConnectionInfo IOConnectionInfo2 { get { return m_ioc2; } } public IOConnectionInfo IOConnectionInfo2 { get { return m_ioc2; } }
private IOAccessType m_t; private readonly IOAccessType m_t;
public IOAccessType Type { get { return m_t; } } public IOAccessType Type { get { return m_t; } }
public IOAccessEventArgs(IOConnectionInfo ioc, IOConnectionInfo ioc2, public IOAccessEventArgs(IOConnectionInfo ioc, IOConnectionInfo ioc2,
@@ -544,4 +547,21 @@ namespace ModernKeePassLib
m_t = t; m_t = t;
} }
} }
public sealed class IOWebRequestEventArgs : EventArgs
{
#if !ModernKeePassLib
private readonly WebRequest m_wr;
public WebRequest Request { get { return m_wr; } }
private readonly IOConnectionInfo m_ioc;
public IOConnectionInfo IOConnectionInfo { get { return m_ioc; } }
public IOWebRequestEventArgs(WebRequest r, IOConnectionInfo ioc)
{
m_wr = r;
m_ioc = ioc;
}
#endif
}
} }

View File

@@ -235,28 +235,28 @@ namespace ModernKeePassLib
None = 0, None = 0,
/// <summary> /// <summary>
/// The IO connection is being opened for reading. /// The I/O connection is being opened for reading.
/// </summary> /// </summary>
Read = 1, Read = 1,
/// <summary> /// <summary>
/// The IO connection is being opened for writing. /// The I/O connection is being opened for writing.
/// </summary> /// </summary>
Write = 2, Write = 2,
/// <summary> /// <summary>
/// The IO connection is being opened for testing /// The I/O connection is being opened for testing
/// whether a file/object exists. /// whether a file/object exists.
/// </summary> /// </summary>
Exists = 3, Exists = 3,
/// <summary> /// <summary>
/// The IO connection is being opened for deleting a file/object. /// The I/O connection is being opened for deleting a file/object.
/// </summary> /// </summary>
Delete = 4, Delete = 4,
/// <summary> /// <summary>
/// The IO connection is being opened for renaming/moving a file/object. /// The I/O connection is being opened for renaming/moving a file/object.
/// </summary> /// </summary>
Move = 5 Move = 5
} }

View File

@@ -1725,7 +1725,7 @@ namespace ModernKeePassLib
{ {
Dictionary<string, bool> d = new Dictionary<string, bool>(); Dictionary<string, bool> d = new Dictionary<string, bool>();
GAction<string> fAdd = delegate(string str) Action<string> fAdd = delegate(string str)
{ {
if(!string.IsNullOrEmpty(str)) d[str] = true; if(!string.IsNullOrEmpty(str)) d[str] = true;
}; };

View File

@@ -9,7 +9,7 @@ namespace ModernKeePassLib.Resources
/// <summary> /// <summary>
/// A strongly-typed resource class, for looking up localized strings, etc. /// A strongly-typed resource class, for looking up localized strings, etc.
/// </summary> /// </summary>
public static class KLRes public static partial class KLRes
{ {
private static string TryGetEx(Dictionary<string, string> dictNew, private static string TryGetEx(Dictionary<string, string> dictNew,
string strName, string strDefault) string strName, string strDefault)

View File

@@ -273,6 +273,7 @@ namespace ModernKeePassLib.Serialization
public static readonly string WrhMoveFileTo = "MoveFileTo"; public static readonly string WrhMoveFileTo = "MoveFileTo";
public static event EventHandler<IOAccessEventArgs> IOAccessPre; public static event EventHandler<IOAccessEventArgs> IOAccessPre;
public static event EventHandler<IOWebRequestEventArgs> IOWebRequestPre;
#if !ModernKeePassLib && !KeePassLibSD #if !ModernKeePassLib && !KeePassLibSD
// Allow self-signed certificates, expired certificates, etc. // Allow self-signed certificates, expired certificates, etc.
@@ -369,6 +370,13 @@ namespace ModernKeePassLib.Serialization
bool? ob = p.GetBool(IocKnownProperties.PreAuth); bool? ob = p.GetBool(IocKnownProperties.PreAuth);
if(ob.HasValue) request.PreAuthenticate = ob.Value; if(ob.HasValue) request.PreAuthenticate = ob.Value;
#endif #endif
if(IOConnection.IOWebRequestPre != null)
{
IOWebRequestEventArgs e = new IOWebRequestEventArgs(request,
((ioc != null) ? ioc.CloneDeep() : null));
IOConnection.IOWebRequestPre(null, e);
}
} }
internal static void ConfigureWebClient(WebClient wc) internal static void ConfigureWebClient(WebClient wc)
@@ -549,13 +557,13 @@ namespace ModernKeePassLib.Serialization
PrepareWebAccess(ioc); PrepareWebAccess(ioc);
IOWebClient wc = new IOWebClient(ioc); IOWebClient wc = new IOWebClient(ioc);
ConfigureWebClient(wc);
if((ioc.UserName.Length > 0) || (ioc.Password.Length > 0)) if((ioc.UserName.Length > 0) || (ioc.Password.Length > 0))
wc.Credentials = new NetworkCredential(ioc.UserName, ioc.Password); wc.Credentials = new NetworkCredential(ioc.UserName, ioc.Password);
else if(NativeLib.IsUnix()) // Mono requires credentials else if(MonoWorkarounds.IsRequired(688007))
wc.Credentials = new NetworkCredential("anonymous", string.Empty); wc.Credentials = new NetworkCredential("anonymous", string.Empty);
ConfigureWebClient(wc);
return wc; return wc;
} }
@@ -564,13 +572,13 @@ namespace ModernKeePassLib.Serialization
PrepareWebAccess(ioc); PrepareWebAccess(ioc);
WebRequest req = WebRequest.Create(ioc.Path); WebRequest req = WebRequest.Create(ioc.Path);
ConfigureWebRequest(req, ioc);
if((ioc.UserName.Length > 0) || (ioc.Password.Length > 0)) if((ioc.UserName.Length > 0) || (ioc.Password.Length > 0))
req.Credentials = new NetworkCredential(ioc.UserName, ioc.Password); req.Credentials = new NetworkCredential(ioc.UserName, ioc.Password);
else if(NativeLib.IsUnix()) // Mono requires credentials else if(MonoWorkarounds.IsRequired(688007))
req.Credentials = new NetworkCredential("anonymous", string.Empty); req.Credentials = new NetworkCredential("anonymous", string.Empty);
ConfigureWebRequest(req, ioc);
return req; return req;
} }

View File

@@ -1,6 +1,6 @@
/* /*
KeePass Password Safe - The Open-Source Password Manager KeePass Password Safe - The Open-Source Password Manager
Copyright (C) 2003-2018 Dominik Reichl <dominik.reichl@t-online.de> Copyright (C) 2003-2020 Dominik Reichl <dominik.reichl@t-online.de>
This program is free software; you can redistribute it and/or modify This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by it under the terms of the GNU General Public License as published by
@@ -336,7 +336,7 @@ namespace ModernKeePassLib.Serialization
#if ModernKeePassLib #if ModernKeePassLib
if (IsLocalFile()) return Bytes != null; if (IsLocalFile()) return Bytes != null;
#else #else
if(IsLocalFile()) return File.Exists(m_strUrl); return IOConnection.FileExists(this, false); // Raises event
#endif #endif
return true; return true;

View File

@@ -22,6 +22,7 @@ using System.Collections.Generic;
using System.Diagnostics; using System.Diagnostics;
using System.IO; using System.IO;
using System.Runtime.CompilerServices; using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
using System.Text; using System.Text;
#if KeePassLibSD #if KeePassLibSD
@@ -820,6 +821,52 @@ namespace ModernKeePassLib.Utility
IDisposable d = (o as IDisposable); IDisposable d = (o as IDisposable);
if(d != null) d.Dispose(); if(d != null) d.Dispose();
} }
internal static T BytesToStruct<T>(byte[] pb, int iOffset)
where T : struct
{
if(pb == null) throw new ArgumentNullException("pb");
if(iOffset < 0) throw new ArgumentOutOfRangeException("iOffset");
int cb = Marshal.SizeOf(typeof(T));
if(cb <= 0) { Debug.Assert(false); return default(T); }
if(iOffset > (pb.Length - cb)) throw new ArgumentOutOfRangeException("iOffset");
IntPtr p = Marshal.AllocCoTaskMem(cb);
if(p == IntPtr.Zero) throw new OutOfMemoryException();
object o;
try
{
Marshal.Copy(pb, iOffset, p, cb);
o = Marshal.PtrToStructure(p, typeof(T));
}
finally { Marshal.FreeCoTaskMem(p); }
return (T)o;
}
internal static byte[] StructToBytes<T>(ref T t)
where T : struct
{
int cb = Marshal.SizeOf(typeof(T));
if(cb <= 0) { Debug.Assert(false); return MemUtil.EmptyByteArray; }
byte[] pb = new byte[cb];
IntPtr p = Marshal.AllocCoTaskMem(cb);
if(p == IntPtr.Zero) throw new OutOfMemoryException();
try
{
Marshal.StructureToPtr(t, p, false);
Marshal.Copy(p, pb, 0, cb);
}
finally { Marshal.FreeCoTaskMem(p); }
return pb;
}
} }
internal sealed class ArrayHelperEx<T> : IEqualityComparer<T[]>, IComparer<T[]> internal sealed class ArrayHelperEx<T> : IEqualityComparer<T[]>, IComparer<T[]>

View File

@@ -180,6 +180,8 @@ namespace ModernKeePassLib.Utility
internal static DialogResult SafeShowMessageBox(string strText, string strTitle, internal static DialogResult SafeShowMessageBox(string strText, string strTitle,
MessageBoxButtons mb, MessageBoxIcon mi, MessageBoxDefaultButton mdb) MessageBoxButtons mb, MessageBoxIcon mi, MessageBoxDefaultButton mdb)
{ {
// strText += MessageService.NewParagraph + (new StackTrace(true)).ToString();
#if KeePassLibSD #if KeePassLibSD
return MessageBox.Show(strText, strTitle, mb, mi, mdb); return MessageBox.Show(strText, strTitle, mb, mi, mdb);
#else #else

View File

@@ -119,10 +119,12 @@ namespace ModernKeePassLib.Utility
// 2140: // 2140:
// Explicit control focusing is ignored. // Explicit control focusing is ignored.
// https://sourceforge.net/p/keepass/feature-requests/2140/ // https://sourceforge.net/p/keepass/feature-requests/2140/
// 5795: // 5795: [Fixed]
// Text in input field is incomplete. // Text in input field is incomplete.
// https://bugzilla.xamarin.com/show_bug.cgi?id=5795 // https://bugzilla.xamarin.com/show_bug.cgi?id=5795
// https://sourceforge.net/p/keepass/discussion/329220/thread/d23dc88b/ // https://sourceforge.net/p/keepass/discussion/329220/thread/d23dc88b/
// https://github.com/mono/mono/commit/1a79065f8cd9f128e6e527e5d573111f794ce288
// https://github.com/mono/mono/pull/5947
// 9604: // 9604:
// Trying to resolve a non-existing metadata token crashes Mono. // Trying to resolve a non-existing metadata token crashes Mono.
// https://github.com/mono/mono/issues/9604 // https://github.com/mono/mono/issues/9604
@@ -162,6 +164,10 @@ namespace ModernKeePassLib.Utility
// 686017: // 686017:
// Minimum sizes must be enforced. // Minimum sizes must be enforced.
// https://bugs.debian.org/cgi-bin/bugreport.cgi?bug=686017 // https://bugs.debian.org/cgi-bin/bugreport.cgi?bug=686017
// 688007: [Fixed]
// Credentials are required for anonymous web requests.
// https://bugzilla.novell.com/show_bug.cgi?id=688007
// https://sourceforge.net/p/keepass/bugs/1950/
// 801414: // 801414:
// Mono recreates the main window incorrectly. // Mono recreates the main window incorrectly.
// https://bugs.launchpad.net/ubuntu/+source/keepass2/+bug/801414 // https://bugs.launchpad.net/ubuntu/+source/keepass2/+bug/801414
@@ -192,13 +198,21 @@ namespace ModernKeePassLib.Utility
if(g_dForceReq.TryGetValue(uBugID, out bForce)) return bForce; if(g_dForceReq.TryGetValue(uBugID, out bForce)) return bForce;
ulong v = NativeLib.MonoVersion; ulong v = NativeLib.MonoVersion;
if(v != 0) if(v == 0) return true;
bool b = true;
switch(uBugID)
{ {
if(uBugID == 10163) case 5795:
return (v >= 0x0002000B00000000UL); // >= 2.11 b = (v < 0x0005000A00000000UL); break;
case 10163:
b = (v >= 0x0002000B00000000UL); break;
case 688007:
b = (v < 0x0006000000000000UL); break;
default: break;
} }
return true; return b;
} }
internal static void SetEnabled(string strIDs, bool bEnabled) internal static void SetEnabled(string strIDs, bool bEnabled)

View File

@@ -320,6 +320,18 @@ namespace ModernKeePassLib.Utility
return str; return str;
} }
internal static string RtfFilterText(string strText)
{
if(strText == null) { Debug.Assert(false); return string.Empty; }
// A U+FFFC character causes the rest of the text to be lost.
// With '?', the string length, substring indices and
// character visibility remain the same.
// More special characters (unproblematic) in rich text boxes:
// https://docs.microsoft.com/en-us/windows/win32/api/richedit/ns-richedit-gettextex
return strText.Replace('\uFFFC', '?');
}
internal static bool ContainsHighChar(string str) internal static bool ContainsHighChar(string str)
{ {
if(str == null) { Debug.Assert(false); return false; } if(str == null) { Debug.Assert(false); return false; }
@@ -975,35 +987,25 @@ namespace ModernKeePassLib.Utility
public static string AddAccelerator(string strMenuText, public static string AddAccelerator(string strMenuText,
List<char> lAvailKeys) List<char> lAvailKeys)
{ {
if(strMenuText == null) { Debug.Assert(false); return null; } if(strMenuText == null) { Debug.Assert(false); return string.Empty; }
if(lAvailKeys == null) { Debug.Assert(false); return strMenuText; } if(lAvailKeys == null) { Debug.Assert(false); return strMenuText; }
int xa = -1, xs = 0; int xa = -1, xs = 0;
for(int i = 0; i < strMenuText.Length; ++i) for(int i = 0; i < strMenuText.Length; ++i)
{ {
char ch = strMenuText[i]; char ch = char.ToLowerInvariant(strMenuText[i]);
#if KeePassLibSD for(int j = 0; j < lAvailKeys.Count; ++j)
char chUpper = char.ToUpper(ch); {
#else if(char.ToLowerInvariant(lAvailKeys[j]) == ch)
char chUpper = char.ToUpperInvariant(ch); {
#endif lAvailKeys.RemoveAt(j);
xa = lAvailKeys.IndexOf(chUpper); return strMenuText.Insert(i, @"&");
if(xa >= 0) { xs = i; break; } }
}
#if KeePassLibSD
char chLower = char.ToLower(ch);
#else
char chLower = char.ToLowerInvariant(ch);
#endif
xa = lAvailKeys.IndexOf(chLower);
if(xa >= 0) { xs = i; break; }
} }
if(xa < 0) return strMenuText; return strMenuText;
lAvailKeys.RemoveAt(xa);
return strMenuText.Insert(xs, @"&");
} }
public static string EncodeMenuText(string strText) public static string EncodeMenuText(string strText)