4

我正在开发一个使用 Bonjour 算法在网络中查找服务的程序。我下载了适用于 Windows 的 Bonjour SDK。.Net 上有两个示例应用程序。两者都是 Windows 窗体项目。示例工作正常,但是当我尝试实现示例控制台应用程序时,我收到了 AccessViolationException。这是我的代码:

class Program
{
    static void Main(string[] args)
    {
        DNSSDService service = new DNSSDService();
        DNSSDEventManager eventManager = new DNSSDEventManager();
        eventManager.ServiceFound += new _IDNSSDEvents_ServiceFoundEventHandler(eventManager_ServiceFound);
        //next line raises AccessViolationException
        DNSSDService browse = service.Browse(0, 0, "_psia._tcp", null, eventManager);

        Console.ReadKey();
    }

    static void eventManager_ServiceFound(DNSSDService browser, DNSSDFlags flags, uint ifIndex, string serviceName, string regtype, string domain)
    {
        //TODO: some logic
    }
}

我找到了解决方案 - Bonjour 库中的所有方法都应该从 STA 线程调用。所以我在 Main 方法中添加了 [STAThread] 属性。代码现在如下所示:

class Program
{
    [STAThread]
    static void Main(string[] args)
    {
        DNSSDService service = new DNSSDService();
        DNSSDEventManager eventManager = new DNSSDEventManager();
        eventManager.ServiceFound += new _IDNSSDEvents_ServiceFoundEventHandler(eventManager_ServiceFound);
        DNSSDService browse = service.Browse(0, 0, "_psia._tcp", null, eventManager);

        Console.ReadKey();
    }

    static void eventManager_ServiceFound(DNSSDService browser, DNSSDFlags flags, uint ifIndex, string serviceName, string regtype, string domain)
    {
        //TODO: some logic
    }
}

我用 AccessViolationException 解决了这个问题,但收到了一个新问题。在我调用 Browse 方法后,应该为网络中定义的每个服务调用“ServiceFound”事件。但它没有。经过一段时间的调查,我发现我需要运行消息泵来接收所有这些事件。所以最终的代码是这样的:

 class Program
{
    [STAThread]
    static void Main(string[] args)
    {
        DNSSDService service = new DNSSDService();
        DNSSDEventManager eventManager = new DNSSDEventManager();
        eventManager.ServiceFound += new _IDNSSDEvents_ServiceFoundEventHandler(eventManager_ServiceFound);
        DNSSDService browse = service.Browse(0, 0, "_psia._tcp", null, eventManager);

        Application.Run();
    }

    static void eventManager_ServiceFound(DNSSDService browser, DNSSDFlags flags, uint ifIndex, string serviceName, string regtype, string domain)
    {
        //TODO: some logic
    }
}

停止消息循环调用 Application.Exit()。

4

1 回答 1

0

我试图用你的代码来发现 ip camera ip address,但我不知道hostName我应该做什么来GetAddrInfo工作。

using Bonjour;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Windows.Forms;

namespace WindowsFormsApplication1 {
    static class Program {
        /// <summary>
        /// The main entry point for the application.
        /// </summary>
        [STAThread]
        static void Main() {
            DNSSDService service = new DNSSDService();
            DNSSDEventManager eventManager = new DNSSDEventManager();
            eventManager.ServiceFound += new _IDNSSDEvents_ServiceFoundEventHandler(eventManager_ServiceFound);
         //   DNSSDService browse = service.Browse(0, 0, "_axis-video._tcp", null, eventManager);
            DNSSDService browse = service.Browse(0, 0, "_http._tcp", null, eventManager);


            Application.EnableVisualStyles();
            Application.SetCompatibleTextRenderingDefault(false);
            Application.Run(new Form1());
        }
        static void eventManager_ServiceFound(DNSSDService browser, DNSSDFlags flags, uint ifIndex, string serviceName, string regtype, string domain) {
            Console.WriteLine("browser: " + browser + "\nDNSSDFlags " +  flags+ "\nifIndex " + ifIndex +"\nserviceName: " + serviceName + "\nregtype: " +regtype+ "\ndomain: "+ domain);

            DNSSDEventManager eventManager = new DNSSDEventManager();
            eventManager.AddressFound += new _IDNSSDEvents_AddressFoundEventHandler(eventManager_AddressFound);
            DNSSDAddressFamily family = new DNSSDAddressFamily();
            browser.GetAddrInfo(flags, ifIndex, family, "axis-00408cbeeae5", eventManager);

        }

        private static void eventManager_AddressFound(DNSSDService service, DNSSDFlags flags, uint ifIndex, string hostname, DNSSDAddressFamily addressFamily, string address, uint ttl) {
            Console.WriteLine("----------------------------------------");
            Console.WriteLine("FFFFFFFFFFFFFFFFFFFFFOUUUUUUUUUUUUUUUUND");
            Console.WriteLine("----------------------------------------");

        }



    }
}
于 2014-01-11T17:40:32.853 回答