为什么安装Office 2013在使用MAPI后会破坏WinForms RichTextBox?

sge*_*218 3 .net mapi pinvoke richtextbox loadlibrary

我有三个程序 -

程序1:另外使用MAPI的Microsoft Outlook加载项.

程序2:使用MAPI 的独立exe

程序3:确实使用MAPI 的独立exe .

这三个程序都是用C#编写的,并且在某些时候使用WinForms RichTextBox.

在使用Office 365程序"1"和"3"的x64 Windows 8安装上没有问题,但只要使用以下堆栈构造RichTextBox控件,程序"2"就会崩溃:

System.IO.FileNotFoundException : C:\Program Files (x86)\Common Files\Microsoft Shared\Office15\riched20.dll
at System.Diagnostics.FileVersionInfo.GetVersionInfo(String fileName)
at System.Windows.Forms.RichTextBox.get_CreateParams()
at System.Windows.Forms.Control..ctor(Boolean autoInstallSyncContext)
at System.Windows.Forms.TextBoxBase..ctor()
at System.Windows.Forms.RichTextBox..ctor()
<snip>
Run Code Online (Sandbox Code Playgroud)

反汇编RichTextBox.get_CreateParams()显示它在'riched20.dll'上调用LoadLibrary,然后在加载的模块上调用GetModuleFileName.

对于程序2,Visual Studio告诉我它已从路径"C:\ Program Files\Microsoft Office 15\root\vfs\ProgramFilesCommonX86\Microsoft Shared\OFFICE15\RICHED20.DLL"加载了riched20.dll.

然后调用FileVersionInfo.GetVersionInfo()失败,因为它给出的路径不存在.

但是 - 程序1(outlook-addin)也从同一路径加载了riched20.dll - 但不知何故成功了!

程序2没有加载MAPI工作正常,它从C:\ Windows\syswow62加载riched20.dll

程序3在创建富文本框之前初始化MAPI,我知道某些MAPI函数会将当前工作目录更改为MAPI目录.这可能解释了为什么程序3加载office的riched20.dll并且程序2加载system32副本.

我怀疑程序1工作和程序3失败的区别在于路径中的vfs代表"虚拟文件系统",因此作为Outlook插件运行的程序1可以某种方式使用不具有的路径找到riched20.dll确实存在.

这三个程序都适用于以前版本的办公室.

作为一种解决方法,在初始化MAPI之前自己调用'LoadLibrary("riched20.dll")会使问题消失 - 但感觉就像一个可怕的黑客.

我也找不到有关此'vfs'文件路径的任何信息以及它在Internet上的含义.

对于我自己的教育,是否有人能够更好地解释这里发生了什么?

更新:我已经解决了与"点击运行"功能有关的问题.

sge*_*218 5

解决方案是在MAPI初始化之前使用pinvoke在'riched20.dll'上调用LoadLibrary.

[DllImport("kernel32", SetLastError = true, CharSet = CharSet.Unicode)]
public static extern IntPtr LoadLibrary(string lpFileName);

LoadLibrary("riched20");
Run Code Online (Sandbox Code Playgroud)