APO动态库DLL文件的路径问题
APO DLL注册路径
APO的DLL文件是通过regsvr32注册表的。比如:
regsvr32.exe xxAPO.dll
这样在注册表HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CLSID就会记录该文件的GUID的路径。
该GUIDPKEY_FX_*EffectClsid
属性的字符串值是CLSID,它标识要实例化以过滤音频信号的特定APO COM类。CLSID是全球唯一的,由sAPO开发人员设置。因此即使在不同的机器和操作系统版本上,它们也可以保持一致。
安装sAPO后,它将在系统范围的COM类存储中注册,该存储位于HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CLSID,以便可以通过其CLSID查找它。
例如,以下命令将查找有关CLSID{EC1CC9CE-FAED-4822-828A-82A81A6F018F}(Equalizer APO)的信息:
$RegistryKey = Get-Item "HKLM:\SOFTWARE\Classes\CLSID\{EC1CC9CE-FAED-4822-828A-82A81A6F018F}"
$RegistryKey.GetValue("")
$RegistryKey.OpenSubKey("InprocServer32").GetValue("")
输出内容为:
EqualizerAPO Post-Mix Class
C:\Program Files\EqualizerAPO\EqualizerAPO.dll
在本例中,EqualizerAPO是包含sAPO代码的dll。Windows音频引擎audiodg.exe进程将加载该DLL以实例化过滤器并处理音频。
APO DLL路径限制
实际上在不同的系统中,这个DLL路径有有些不同的。
比如本人在Windows10 1607系统中,是可以将该DLL在用户桌面注册并加载的。但是在1809系统中,系统会因为无权该问用户目录而加载DLL失败。这是因为:APO运行于audiodg.exe进程内部,而该进程本身在Windows音频服务(Audiosrv)下运行。与几乎所有服务一样,此服务不在您的普通Windows用户帐户下运行。相反,它的访问令牌授予它的权限大致相当于LocalService帐户。所以出于安全和隔离原因,该服务无法访问您的用户目录(即C:\Users\<username>)。
在某些情况下,这可能导致APO行为失常,因为它试图打开一个不允许访问的文件(或其他安全对象,如注册表项)。
一个示例是将均衡器APO配置文件存储在用户目录中。在这种情况下,均衡器APO配置编辑器将显示一个有用的警告,APO本身将在其日志文件(C:\Windows\ServiceProfiles\LocalService\AppData\Local\Temp\EqualizerAPO.log)中记录一条错误消息。
下面使用Process Monitor来排查APO的加载权限:
使用的过滤条件为:
- “Process Name” is audiodg.exe
- “Result” is ACCESS DENIED
然后重新启动Windows音频服务AudioSvr并开始流式播放音频。然后,访问被拒绝错误应出现在Process Monitor中。
以下示例显示Equalizer APO试图打开无法访问的配置文件:
通过查看Process Monitor中的事件堆栈,可以确定哪个DLL正在进行有问题的调用。在本例中,它是EqualizerAPO.dll,如预期。如果故障源于Equalizer APO中使用的VST,则堆栈应在Equalifier APO旁边(或代替)提及有问题的VST DLL。
可以使用2种方法来解决这个访问权限问题:
- 将有问题的文件/对象移动到音频服务可以访问的位置。例如Program Files或ProgramData。或者:
- 更改有问题的文件/对象的权限(DACL),以允许音频服务访问。
要调整权限,请转到有问题的文件/对象(或父对象)的安全属性,并确保NT SERVICE\Audiosrv用户主体具有访问权限。(此主体是服务SID。您也可以使用本地服务帐户,但只允许Windows音频服务更干净。)
然后重新启动Windows音频服务。
注意:虽然此技术可用于在标准配置目录之外存储Equalizer APO配置文件,但请记住,这样做将破坏Equalifier APO的“即时模式”功能(即实时更改),因为Equalize APO仅监视其配置目录的更改。