GraphEngine中的死锁

问题描述:

使用GraphEngine有一段时间我经常在对GraphEngine执行一些操作时发现自己有死锁线程。嵌套调用绝对不在菜单上。但现在我遇到一些奇怪的事情:GraphEngine中的死锁

foreach(long cellID ...) 
{ 
    byte[] buffer; 

    // the next line will block on the 54th call... 
    Global.LocalStorage.LoadCell(cellID, out buffer); 
} 

疑不存在的CellID我的调用包装与

if(Global.LocalStorage.Contains(cellID)) 
{ ... } 

但是现在这个调用块indefinitly。

这是一个错误?或

呼叫阻塞在哪些情况下会发生?

Cheerio, Andreas。

@Andreas Hassmann,我遇到了类似的问题,所以我想你的麻烦可能是由foreach循环中的...造成的。

我使用了一个迭代器,如Global.LocalStorage.xxxCell_Accessor_Selector().Select(c => c.CellID.Value)。在这种情况下,当Global.LocalStorage.LoadCell()获取锁时,存储的锁没有被释放,导致死锁。

如果您的问题与我的问题完全相同,则解决方案将为.ToList()应用于迭代器。

这里是我的代码来重现您的问题。

的TSL:

cell struct MyCell 
{ 
    int A; 
} 

的代码:

for (int i = 0; i < 100; i++) 
{ 
    MyCell mc = new MyCell(i); 
    Global.LocalStorage.SaveMyCell(i, mc); 
} 

var ids = Global.LocalStorage.MyCell_Accessor_Selector().Select(c => c.CellID.Value); 

Console.WriteLine("1 start."); 
foreach (long cellID in ids.ToList()) 
{ 
    byte[] buffer; 
    Global.LocalStorage.LoadCell(cellID, out buffer); 
    Console.WriteLine(cellID); 
} 
Console.WriteLine("1 done."); 

Console.WriteLine("2 start."); 
foreach (long cellID in ids) 
{ 
    byte[] buffer; 
    Global.LocalStorage.LoadCell(cellID, out buffer); 
    Console.WriteLine(cellID); 
} 
Console.WriteLine("2 done."); 
+0

谢谢,L.H.!我必须道歉,因为我的问题过于简单。我的CellID来自迭代不同的CellType,LoadCell在第54次呼叫时被阻塞,而不是第一次。这就是我怀疑违规的原因。但是,我也用ToList()来规避它。但是,如果它们存在,这将使Trinity内的任何聪明的迭代器实现都无用。 –

+0

@AndreasHassmann我看到你想要什么,我找到了另一个解决方案:如果我们不想更新迭代器中的任何数据,我们可以将Trinity存储设置为“只读”模式,这将启用任意操作而不用担心锁。我的解决方案是首先初始化存储并将存储保存到磁盘,然后在加载和迭代存储之前放置这些代码: 'TrinityConfig.CurrentRunningMode = RunningMode.Embedded; TrinityConfig.ReadOnly = true; Global.LocalStorage.LoadStorage();' –

+0

再次感谢,L.H.这听起来好像它不能在运行时切换,对吧?我将不得不重新连接到数据库。你是梁何?我想和一个建立它的人讨论一下Trinity,而不会在这里的公共空间乱扔垃圾...... –