LoadIFilter()在所有PDF上都失败(但MS的filtdump.exe没有。)

时间:2011-08-24 15:18:52

标签: c# interop ifilter

我正在尝试编写一个C#实用程序,它模仿Windows Search SDK中filtdump.exe的行为(因为filtdump本身似乎不是可再发行的。)我遇到了结合矛盾和/或不存在的文档和技术问题我似乎无法追查。我希望有人可以帮助消除这些障碍中的一个......

根据MSDN,filtdump使用ILoadFilter::LoadIFilter加载它的IFilter。我认为MSDN撒谎,因为它声称ILoadFilter::LoadIFilter仅存在于Windows 7上,但filtdump在earler OS上运行正常。进程监视器表明它实际上是从LoadIFilter()调用query.dll,所以这就是我正在做的事情:

public static class NativeMethods
{
    // From Windows SDK v7.1, NTQuery.h
    [DllImport("query.dll", CharSet = CharSet.Unicode)]
    public static extern int LoadIFilter(
        string pwcsPath,
        [MarshalAs(UnmanagedType.IUnknown)] 
        ref object pUnkOuter,
        ref IFilter ppIUnk);
}

object iUnknown = null;
IFilter filter = null;
var result = NativeMethods.LoadIFilter(args[0], ref iUnknown, ref filter);
if (result != ResultCodes.S_OK)
{
  Console.WriteLine("Failed to load an IFilter for {0}: {1}", args[0], result);
  return;
}

在大多数情况下,此应用程序和filtdump给出了相同的结果 - 它们可以打开文本,从Word文档和Outlook电子邮件中提取和提取文本,并且在同一组其他文档中都失败没有IFilter。但是,PDF正在给我一个问题。 Filtdump设法打开并从我抛出的大部分PDF中提取文本,但是我用自己的应用程序尝试的每一个PDF都给出了HRESULT为0x80004005,E_FAIL。

这是来自this question的相同错误,但是我在每个 PDF上得到它,filtdump不是,所以我知道IFilter正在处理至少一些文件。有没有人以前用PDF做过这种事情,可以看出我做错了什么?

3 个答案:

答案 0 :(得分:3)

您可能希望看到this blog post。简而言之,Adobe的PDF过滤器v10使用允许使用过滤器的白名单,包括微软的filtdump.exe等诊断工具,据称是一种“安全措施”。

答案 1 :(得分:1)

加载IFilter失败,因为Adove PDF过滤器被标记为STA,我们的c应用程序默认为MTA,因此无法加载PDF过滤器。尝试使您的应用程序STA加载PDF过滤器。

的Ajax

答案 2 :(得分:0)

我还希望filtdump使用Windows 2000中提供的旧版Win32 LoadIFilter call

通过在作业中运行调用进程,我看到了同样的问题。 https://stackoverflow.com/a/8841476/1111659

虽然Win32 LoadIFilter()返回的是E_NOTIMPL而不是E_FAIL,但我在安装Reader 10.1.5时也遇到了类似的问题。

似乎Adobe打破了标准的Win32 LoadIFilter()调用,删除了通过IStorage接口的Load方法将内容加载到IFilter中的功能,但该对象仍然通过QI返回该接口。

对于Windows 7及更高版本上的该问题,您可以创建实现ILoadFilter的FilterRegistration对象,然后调用ILoadFilter :: LoadIFilter()来创建过滤器COM对象。然后获取IPersistStream并使用包含文件内容的IStream调用Load()。

对于旧版本,您需要首先在注册表中搜索Filter CLSID,或者如果要使其保持不变,请将Adobe CLSID静态设置为配置值。