设备销毁处理
This commit is contained in:
@@ -15,11 +15,12 @@ namespace UIShare.GlobalVariable
|
||||
/// 设备管理器:根据 <see cref="SystemConfig.DeviceList"/> 反射实例化所有启用的设备,
|
||||
/// 通过 <see cref="IBaseInterface"/> 多态统一管理,避免为每种设备单独硬编码字段。
|
||||
/// </summary>
|
||||
public class DeviceManager
|
||||
public class DeviceManager:IDisposable
|
||||
{
|
||||
private object _lockObj = new object();
|
||||
public SystemConfig _systemConfig { get; set; }
|
||||
private readonly GlobalInfo _globalInfo;
|
||||
private readonly string _scopeName;
|
||||
|
||||
/// <summary>按 DeviceName 索引的设备字典,便于业务层按名取实例。</summary>
|
||||
public IDictionary<string, IBaseInterface> DeviceMap { get; private set; }
|
||||
@@ -32,6 +33,8 @@ namespace UIShare.GlobalVariable
|
||||
{
|
||||
_systemConfig = systemConfig;
|
||||
_globalInfo = globalInfo;
|
||||
// 用 SystemConfig.Title 作为作用域唯一标识,无需反查 ConfigDic
|
||||
_scopeName = _systemConfig.Title;
|
||||
InitDevices();
|
||||
}
|
||||
/// <summary>
|
||||
@@ -108,6 +111,18 @@ namespace UIShare.GlobalVariable
|
||||
DeviceMap[config.DeviceName] = instance;
|
||||
}
|
||||
|
||||
// 第五步:将当前作用域注册到指纹的作用域列表,用于引用计数与安全销毁
|
||||
if (!string.IsNullOrEmpty(_scopeName))
|
||||
{
|
||||
var scopeList = _globalInfo.DeviceAndScopeDic.GetOrAdd(fingerprint,
|
||||
_ => new Lazy<List<string>>(() => new List<string>())).Value;
|
||||
lock (scopeList)
|
||||
{
|
||||
if (!scopeList.Contains(_scopeName))
|
||||
scopeList.Add(_scopeName);
|
||||
}
|
||||
}
|
||||
|
||||
LoggerHelper.Info($"已加载设备 [{config.DeviceName} / {config.DeviceType} / {config.ConnectionType}] 指纹={fingerprint}");
|
||||
}
|
||||
catch (Exception ex)
|
||||
@@ -338,6 +353,50 @@ namespace UIShare.GlobalVariable
|
||||
};
|
||||
return Activator.CreateInstance(type, cfg) as IBaseInterface;
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
if (string.IsNullOrEmpty(_scopeName)) return;
|
||||
|
||||
// 遍历当前作用域用到的所有指纹,逐一移除本作用域的引用
|
||||
var fingerprintsToRemove = new List<string>();
|
||||
|
||||
foreach (var kvp in _globalInfo.DeviceAndScopeDic)
|
||||
{
|
||||
string fingerprint = kvp.Key;
|
||||
var scopeList = kvp.Value.IsValueCreated ? kvp.Value.Value : null;
|
||||
if (scopeList == null) continue;
|
||||
|
||||
lock (scopeList)
|
||||
{
|
||||
scopeList.Remove(_scopeName);
|
||||
|
||||
// 引用归零 → 标记为待清理
|
||||
if (scopeList.Count == 0)
|
||||
fingerprintsToRemove.Add(fingerprint);
|
||||
}
|
||||
}
|
||||
|
||||
// 对引用归零的指纹:销毁设备实例 + 从全局池中移除
|
||||
foreach (var fingerprint in fingerprintsToRemove)
|
||||
{
|
||||
// 尝试从 HardwarePool 取出并销毁
|
||||
if (_globalInfo.HardwarePool.TryRemove(fingerprint, out var lazy))
|
||||
{
|
||||
if (lazy.IsValueCreated && lazy.Value is IBaseInterface device)
|
||||
{
|
||||
try { device.Close(); }
|
||||
catch { /* 销毁时忽略异常 */ }
|
||||
LoggerHelper.Info($"指纹 [{fingerprint}] 无作用域引用,已销毁设备实例。");
|
||||
}
|
||||
}
|
||||
|
||||
// 同步清除 DeviceAndScopeDic 中的空条目
|
||||
_globalInfo.DeviceAndScopeDic.TryRemove(fingerprint, out _);
|
||||
}
|
||||
|
||||
DeviceMap.Clear();
|
||||
}
|
||||
#endregion
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user