移动宽带API:“;需要引脚”;异常,但pin已设置

本文关键字:异常 设置 pin 引脚 API 移动 | 更新日期: 2023-09-27 18:29:28

我正试着起床&与移动宽带API一起运行。我从C#使用它,使用这里的说明。

不过,我有一个问题:当调制解调器设备被锁定时(即,需要PIN),我想以编程方式设置PIN,然后继续进行连接,但后者以"需要PIN"失败,即使我刚刚正确设置了PIN。

移动宽带API提供IMbnPin接口来设置引脚,但这是一个异步操作,因此您必须注册OnEnterComplete事件(IMbnPinEvents接口的一部分),该事件表示操作已完成。我以为这就足够了,但显然还不够。

下面的类是一个最小的、自包含的示例,用于演示这个问题。您可以在控制台应用程序中使用它,如下所示:

var testInstance = new MbnTest();
testInstance.Test("XXXX"); // replace with actual PIN code

(你还需要一个Interop dll来编译它,你可以在这里找到)

测试类包含一个ManualResetEvent字段,用于在Enter和OnEnterComplete方法之间进行协调。

在Test方法中,我订阅IMbnPinEvents,实例化IMbnPin,调用(异步)Enter方法,并调用ManualResetEvent.WaitOne来阻塞当前线程。在OnEnterComplete中,我可以验证引脚是否正确设置,然后向ManualResetEvent发出信号,以便Test方法继续执行。如果我在那之后立即继续TryToGetConnectionState()调用,我会得到一个异常E_MBN_PIN_REQUIRED(0x80548210)。如果我使用Console.ReadLine()等待"足够长的时间",一切都会正常工作。所以看起来我需要等待另一个活动,但我找不到哪一个。

有什么想法吗?我错过了什么?

// warning: this is sample code, needs to be better structured for production use
class MbnTest : IMbnPinEvents
{
    private readonly ManualResetEvent _resetEventPin = new ManualResetEvent(false);
    public void Test(string pinCode)
    {
        var interfacemanager = (IMbnInterfaceManager)new MbnInterfaceManager();
        SubscribeToPinEvents(interfacemanager);
        var mbnPin = GetPin(interfacemanager);
        uint requestId;
        Trace.WriteLine("Setting PIN");
        mbnPin.Enter(pinCode, out requestId);
        Trace.WriteLine("Waiting for OnEnterComplete");
        // wait for the OnEnterComplete event
        _resetEventPin.WaitOne();
        Trace.WriteLine("press enter to retrieve connection state");
        Console.ReadLine();
        TryToGetConnectionState();
    }
    void IMbnPinEvents.OnEnterComplete(IMbnPin pin, ref MBN_PIN_INFO pinInfo, uint requestID, int status)
    {
        // reports MBN_PIN_STATE_NONE which means no pin is required
        Trace.WriteLine(string.Format("OnEnterComplete: pin state = {0}", pinInfo.pinState));
        // signal the ManualResetEvent to unblock the thread waiting for the Enter Pin operation to complete
        _resetEventPin.Set();
    }
    private void SubscribeToPinEvents(IMbnInterfaceManager interfacemanager)
    {
        Trace.WriteLine("Subscribing to IMbnPinEvents");
        var guidPinEvents = typeof (IMbnPinEvents).GUID;
        var connectionPointContainer = (IConnectionPointContainer) interfacemanager;
        IConnectionPoint connectionPoint;
        connectionPointContainer.FindConnectionPoint(ref guidPinEvents, out connectionPoint);
        uint cookie;
        connectionPoint.Advise(this, out cookie);
    }
    private static IMbnPin GetPin(IMbnInterfaceManager interfacemanager)
    {
        IMbnInterface mbnInterface = interfacemanager.GetInterfaces().OfType<IMbnInterface>().First();
        Trace.WriteLine(string.Format("mbnInterface: {0}", mbnInterface.GetReadyState()));
        var pinMgr = (IMbnPinManager)mbnInterface;
        var mbnPin = pinMgr.GetPin(MBN_PIN_TYPE.MBN_PIN_TYPE_PIN1);
        return mbnPin;
    }
    private static void TryToGetConnectionState()
    {
        Trace.WriteLine("Retrieving mbn connection");
        var connectionManager = (IMbnConnectionManager)new MbnConnectionManager();
        var mbnConnection = connectionManager.GetConnections().OfType<IMbnConnection>().First();
        Trace.WriteLine(string.Format("connection: {0}", mbnConnection.ConnectionID));
        MBN_ACTIVATION_STATE state;
        string profilename;
        mbnConnection.GetConnectionState(out state, out profilename);
    }

    void IMbnPinEvents.OnChangeComplete(IMbnPin pin, ref MBN_PIN_INFO pinInfo, uint requestID, int status)
    {
        throw new NotImplementedException();
    }
    void IMbnPinEvents.OnEnableComplete(IMbnPin pin, ref MBN_PIN_INFO pinInfo, uint requestID, int status)
    {
        throw new NotImplementedException();
    }
    void IMbnPinEvents.OnDisableComplete(IMbnPin pin, ref MBN_PIN_INFO pinInfo, uint requestID, int status)
    {
        throw new NotImplementedException();
    }

    void IMbnPinEvents.OnUnblockComplete(IMbnPin pin, ref MBN_PIN_INFO pinInfo, uint requestID, int status)
    {
        throw new NotImplementedException();
    }
}

移动宽带API:“;需要引脚”;异常,但pin已设置

我找到了答案:在建立连接之前,我需要等待网络注册变为活动状态。事后看来有点明显。为了使它发挥作用,我做了以下更改:

  • 在设置引脚之前,请订阅IMbnRegistrationEvents接口
  • IMbnRegistrationEvents.OnRegisterStateChange方法中,检查注册状态为"已注册"(即值MBN_REGISTER_state_HOME之一,MBN_REGISTER_STATE_ROAMING或MBN_REGISTER_STATE_PARTNER)

从那时起,您可以使用IMbnConnection.Connect方法创建宽带连接。

很难找到关于这方面的文档。。。msdn上有《移动宽带连接管理器开发指南》,但我在里面找不到任何细节。此外,我不确定这种行为是否有任何特定于提供商或设备的行为。