Ich versuche, ein Mutex
mit einer IDisposable
Klasse wie folgt zu wickeln:Wrapping ein Mutex mit IDisposable und es zu testen, aber der Test endet nie
public class NamedMutex : IDisposable
{
private static readonly object _syncLock = new object();
private readonly Mutex _namedMutex;
private readonly bool _createdNew;
public NamedMutex(string name)
{
if (string.IsNullOrEmpty(name)) throw new ArgumentNullException("name");
//lock (_syncLock)
{
_namedMutex = new Mutex(initiallyOwned: false, name: name, createdNew: out _createdNew);
}
_namedMutex.WaitOne();
}
public void Dispose()
{
//lock (_syncLock)
{
//if (_createdNew)
_namedMutex.ReleaseMutex();
_namedMutex.Dispose();
}
}
}
, wie Sie aus dem Kommentar gesetzt Code sehen ich habe habe so ziemlich alles ausprobiert, was ich mir vorstellen konnte, aber entweder ist mein Test falsch oder etwas stimmt nicht mit der obigen Implementierung, weil der Test nie endet (wahrscheinlich ein Deadlock, den ich nicht identifizieren kann oder mit dem es abstürzt) unsynchronisierte Ausnahme).
Dies ist mein Test, den ich für LINQPad angepasst:
void Main()
{
var sw = Stopwatch.StartNew();
var task1 = Task.Run(async() =>
{
using (new NamedMutex("foo"))
{
Console.WriteLine(3);
await Task.Delay(TimeSpan.FromSeconds(3));
}
});
var task2 = Task.Run(async() =>
{
using (new NamedMutex("foo"))
{
Console.WriteLine(2);
await Task.Delay(TimeSpan.FromSeconds(2));
}
});
Task.WaitAll(task1, task2);
//Assert.IsTrue(sw.Elapsed.TotalSeconds >= 5);
sw.Elapsed.Dump(); // LINQPad
}
Können Sie setzen einen Haltepunkt im Konstruktor von '' 'NamedMutex''' und uns sagen, ob es jemals bekommt hinter der' '' _namedMutex.WaitOne(); '' 'Linie? –
@MattThomas ja es tut. Wenn ich 'Console.WriteLine (" WaitOne ") hinzufüge;' wird darunter 'WaitOne' nur einmal, dann sofort' 3' gedruckt und es bleibt für immer hängen. – t3chb0t
Ich habe das gerade im Visual Studio getestet, und es funktioniert beim ersten Mal korrekt, aber alle nachfolgenden Versuche scheitern. Wenn Sie dann den Namen des Mutex ändern, funktioniert es erneut einmal und schlägt bei nachfolgenden Aufrufen erneut fehl. Es scheint, dass der Mutex nach dem Programmende nicht richtig entsorgt wird. –