static uint8_t AJRouter_Connect(AJ_BusAttachment* busAttachment, const char* routerName)
{
    AJ_Status status;
    const char* busUniqueName;

    while (TRUE) {
        AJ_InfoPrintf(("Attempting to connect to bus '%s'\n", routerName));
        status = AJ_FindBusAndConnect(busAttachment, routerName, AJAPP_CONNECT_TIMEOUT);
        if (status != AJ_OK) {
            AJ_InfoPrintf(("Failed to connect to bus sleeping for %d seconds\n", AJAPP_CONNECT_PAUSE / 1000));
            AJ_Sleep(AJAPP_CONNECT_PAUSE);
            continue;
        }
        busUniqueName = AJ_GetUniqueName(busAttachment);
        if (busUniqueName == NULL) {
            AJ_ErrPrintf(("Failed to GetUniqueName() from newly connected bus, retrying\n"));
            continue;
        }
        AJ_InfoPrintf(("Connected to router with BusUniqueName=%s\n", busUniqueName));
        break;
    }

    /* Setup password based authentication listener for secured peer to peer connections */
    AJ_BusSetPasswordCallback(busAttachment, PasswordCallback);

    /* Configure timeout for the link to the Router bus */
    AJ_SetBusLinkTimeout(busAttachment, 60);     // 60 seconds

    return TRUE;
}
AJ_Status AJServices_ConnectedHandler(AJ_BusAttachment* busAttachment)
{
    AJ_BusSetPasswordCallback(busAttachment, PasswordCallback);
    /* Configure timeout for the link to the Router bus */
    AJ_SetBusLinkTimeout(busAttachment, 60);     // 60 seconds

    AJ_Status status = AJ_OK;

    status = AJ_About_ConnectedHandler(busAttachment);
    if (status != AJ_OK) {
        goto ErrorExit;
    }
#ifdef CONFIG_SERVICE

    status = AJCFG_ConnectedHandler(busAttachment);
    if (status != AJ_OK) {
        goto ErrorExit;
    }
#endif
#ifdef ONBOARDING_SERVICE

    status = AJOBS_ConnectedHandler(busAttachment);
    if (status != AJ_OK) {
        goto ErrorExit;
    }
#endif
#ifdef NOTIFICATION_SERVICE_PRODUCER

    status = AJNS_Producer_ConnectedHandler(busAttachment);
    if (status != AJ_OK) {
        goto ErrorExit;
    }
#endif
#ifdef CONTROLPANEL_SERVICE

    status = AJCPS_ConnectedHandler(busAttachment);
    if (status != AJ_OK) {
        goto ErrorExit;
    }
#endif
#ifdef NOTIFICATION_SERVICE_CONSUMER

    status = AJNS_Consumer_ConnectedHandler(busAttachment);
    if (status != AJ_OK) {
        goto ErrorExit;
    }
#endif
    return status;

ErrorExit:

    AJ_AlwaysPrintf(("Service ConnectedHandler returned an error %s\n", (AJ_StatusText(status))));
    return status;
}
示例#3
0
文件: aj_helper.c 项目: reignme/ajtcl
AJ_Status AJ_RunAllJoynService(AJ_BusAttachment* bus, AllJoynConfiguration* config)
{
    uint8_t connected = FALSE;
    AJ_Status status = AJ_OK;

    while (TRUE) {
        AJ_Time start = { 0, 0 };
        AJ_Message msg;
        uint32_t now;
        // get the next timeout
        //Timer* timer = GetNextTimeout();
        uint32_t next;
        // wait forever
        uint32_t timeout = (uint32_t) -1;

        if (!connected) {
            status = AJ_StartService2(
                bus,
                config->daemonName, config->connect_timeout, config->connected,
                config->session_port, config->service_name, config->flags, config->opts);
            if (status != AJ_OK) {
                continue;
            }
            AJ_InfoPrintf(("StartService returned AJ_OK\n"));
            AJ_InfoPrintf(("Connected to Daemon:%s\n", AJ_GetUniqueName(bus)));

            connected = TRUE;

            /* Register a callback for providing bus authentication password */
            AJ_BusSetPasswordCallback(bus, config->password_callback);

            /* Configure timeout for the link to the daemon bus */
            AJ_SetBusLinkTimeout(bus, config->link_timeout);

            if (config->connection_handler != NULL) {
                (config->connection_handler)(connected);
            }
        }

        // absolute time in milliseconds
        now = AJ_GetElapsedTime(&start, FALSE);
        next = RunExpiredTimers(now);

        if (next != (uint32_t) -1) {
            // if no timers running, wait forever
            timeout = next;
        }

        status = AJ_UnmarshalMsg(bus, &msg, min(500, timeout));
        if (AJ_ERR_TIMEOUT == status && AJ_ERR_LINK_TIMEOUT == AJ_BusLinkStateProc(bus)) {
            status = AJ_ERR_READ;
        }

        if (status == AJ_ERR_TIMEOUT) {
            // go back around and handle the expired timers
            continue;
        }

        if (status == AJ_OK) {
            uint8_t handled = FALSE;
            const MessageHandlerEntry* message_entry = config->message_handlers;
            const PropHandlerEntry* prop_entry = config->prop_handlers;

            // check the user's handlers first.  ANY message that AllJoyn can handle is override-able.
            while (handled != TRUE && message_entry->msgid != 0) {
                if (message_entry->msgid == msg.msgId) {
                    if (msg.hdr->msgType == AJ_MSG_METHOD_CALL) {
                        // build a method reply
                        AJ_Message reply;
                        status = AJ_MarshalReplyMsg(&msg, &reply);

                        if (status == AJ_OK) {
                            status = (message_entry->handler)(&msg, &reply);
                        }

                        if (status == AJ_OK) {
                            status = AJ_DeliverMsg(&reply);
                        }
                    } else {
                        // call the handler!
                        status = (message_entry->handler)(&msg, NULL);
                    }

                    handled = TRUE;
                }

                ++message_entry;
            }

            // we need to check whether this is a property getter or setter.
            // these are stored in an array because multiple getters and setters can exist if running more than one bus object
            while (handled != TRUE && prop_entry->msgid != 0) {
                if (prop_entry->msgid == msg.msgId) {
                    // extract the method from the ID; GetProperty or SetProperty
                    uint32_t method = prop_entry->msgid & 0x000000FF;
                    if (method == AJ_PROP_GET) {
                        status = AJ_BusPropGet(&msg, prop_entry->callback, prop_entry->context);
                    } else if (method == AJ_PROP_SET) {
                        status = AJ_BusPropSet(&msg, prop_entry->callback, prop_entry->context);
                    } else {
                        // this should never happen!!!
                        AJ_ASSERT(!"Invalid property method");
                    }

                    handled = TRUE;
                }

                ++prop_entry;
            }

            // handler not found!
            if (handled == FALSE) {
                if (msg.msgId == AJ_METHOD_ACCEPT_SESSION) {
                    uint8_t accepted = (config->acceptor)(&msg);
                    status = AJ_BusReplyAcceptSession(&msg, accepted);
                } else {
                    status = AJ_BusHandleBusMessage(&msg);
                }
            }

            // Any received packets indicates the link is active, so call to reinforce the bus link state
            AJ_NotifyLinkActive();
        }
        /*
         * Unarshaled messages must be closed to free resources
         */
        AJ_CloseMsg(&msg);

        if (status == AJ_ERR_READ) {
            AJ_InfoPrintf(("AllJoyn disconnect\n"));
            AJ_InfoPrintf(("Disconnected from Daemon:%s\n", AJ_GetUniqueName(bus)));
            AJ_Disconnect(bus);
            connected = FALSE;
            if (config->connection_handler != NULL) {
                (config->connection_handler)(connected);
            }
            /*
             * Sleep a little while before trying to reconnect
             */
            AJ_Sleep(10 * 1000);
        }
    }

    // this will never actually return!
    return AJ_OK;
}
示例#4
0
文件: svclite.c 项目: fonlabs/ajtcl
int AJ_Main()
{
    AJ_Status status = AJ_OK;
    AJ_BusAttachment bus;
    uint8_t connected = FALSE;
    uint32_t sessionId = 0;

    /*
     * One time initialization before calling any other AllJoyn APIs
     */
    AJ_Initialize();

    AJ_PrintXML(AppObjects);
    AJ_RegisterObjects(AppObjects, NULL);

    SetBusAuthPwdCallback(MyBusAuthPwdCB);
    while (TRUE) {
        AJ_Message msg;

        if (!connected) {
            status = AJ_StartService(&bus, NULL, CONNECT_TIMEOUT, FALSE, ServicePort, ServiceName, AJ_NAME_REQ_DO_NOT_QUEUE, NULL);
            if (status != AJ_OK) {
                continue;
            }
            AJ_InfoPrintf(("StartService returned AJ_OK\n"));
            AJ_InfoPrintf(("Connected to Daemon:%s\n", AJ_GetUniqueName(&bus)));

            connected = TRUE;
#ifdef SECURE_OBJECT
            status = AJ_SetObjectFlags("/org/alljoyn/alljoyn_test", AJ_OBJ_FLAG_SECURE, 0);
            if (status != AJ_OK) {
                AJ_ErrPrintf(("Error calling AJ_SetObjectFlags.. [%s] \n", AJ_StatusText(status)));
                return -1;
            }
#endif

#if defined(SECURE_INTERFACE) || defined(SECURE_OBJECT)

            /* Register a callback for providing bus authentication password */
            AJ_BusSetPasswordCallback(&bus, PasswordCallback);
            AJ_BusEnableSecurity(&bus, suites, numsuites);
            AJ_BusSetAuthListenerCallback(&bus, AuthListenerCallback);
#endif

            /* Configure timeout for the link to the daemon bus */
            AJ_SetBusLinkTimeout(&bus, 60); // 60 seconds
        }

        status = AJ_UnmarshalMsg(&bus, &msg, UNMARSHAL_TIMEOUT);
        if (AJ_ERR_TIMEOUT == status && AJ_ERR_LINK_TIMEOUT == AJ_BusLinkStateProc(&bus)) {
            status = AJ_ERR_READ;
        }
        if (status != AJ_OK) {
            if (status == AJ_ERR_TIMEOUT) {
                AppDoWork();
                continue;
            }
        }

        if (status == AJ_OK) {
            switch (msg.msgId) {

            case AJ_REPLY_ID(AJ_METHOD_ADD_MATCH):
                if (msg.hdr->msgType == AJ_MSG_ERROR) {
                    AJ_InfoPrintf(("Failed to add match\n"));
                    status = AJ_ERR_FAILURE;
                } else {
                    status = AJ_OK;
                }
                break;

            case AJ_METHOD_ACCEPT_SESSION:
                {
                    uint16_t port;
                    char* joiner;
                    AJ_UnmarshalArgs(&msg, "qus", &port, &sessionId, &joiner);
                    if (port == ServicePort) {
                        status = AJ_BusReplyAcceptSession(&msg, TRUE);
                        AJ_InfoPrintf(("Accepted session session_id=%u joiner=%s\n", sessionId, joiner));
                    } else {
                        status = AJ_BusReplyAcceptSession(&msg, FALSE);
                        AJ_InfoPrintf(("Accepted rejected session_id=%u joiner=%s\n", sessionId, joiner));
                    }
                }
                break;

            case APP_MY_PING:
                status = AppHandlePing(&msg);
                break;

            case APP_GET_PROP:
                status = AJ_BusPropGet(&msg, PropGetHandler, NULL);
                break;

            case APP_SET_PROP:
                status = AJ_BusPropSet(&msg, PropSetHandler, NULL);
                if (status == AJ_OK) {
                    AJ_InfoPrintf(("Property successfully set to %d.\n", propVal));
                } else {
                    AJ_InfoPrintf(("Property set attempt unsuccessful. Status = 0x%04x.\n", status));
                }
                break;

            case AJ_SIGNAL_SESSION_LOST_WITH_REASON:
                {
                    uint32_t id, reason;
                    AJ_UnmarshalArgs(&msg, "uu", &id, &reason);
                    AJ_InfoPrintf(("Session lost. ID = %u, reason = %u", id, reason));
                    if (CancelAdvertiseName) {
                        status = AJ_BusAdvertiseName(&bus, ServiceName, AJ_TRANSPORT_ANY, AJ_BUS_START_ADVERTISING, 0);
                    }
                    status = AJ_ERR_SESSION_LOST;
                }
                break;

            case AJ_SIGNAL_SESSION_JOINED:
                if (CancelAdvertiseName) {
                    status = AJ_BusAdvertiseName(&bus, ServiceName, AJ_TRANSPORT_ANY, AJ_BUS_STOP_ADVERTISING, 0);
                }
                break;

            case AJ_REPLY_ID(AJ_METHOD_CANCEL_ADVERTISE):
            case AJ_REPLY_ID(AJ_METHOD_ADVERTISE_NAME):
                if (msg.hdr->msgType == AJ_MSG_ERROR) {
                    status = AJ_ERR_FAILURE;
                }
                break;

            case APP_MY_SIGNAL:
                AJ_InfoPrintf(("Received my_signal\n"));
                status = AJ_OK;

                if (ReflectSignal) {
                    AJ_Message out;
                    AJ_MarshalSignal(&bus, &out, APP_MY_SIGNAL, msg.destination, msg.sessionId, 0, 0);
                    AJ_MarshalArgs(&out, "a{ys}", 0, NULL);
                    AJ_DeliverMsg(&out);
                    AJ_CloseMsg(&out);
                }
                break;

            default:
                /*
                 * Pass to the built-in bus message handlers
                 */
                status = AJ_BusHandleBusMessage(&msg);
                break;
            }

            // Any received packets indicates the link is active, so call to reinforce the bus link state
            AJ_NotifyLinkActive();
        }
        /*
         * Unarshaled messages must be closed to free resources
         */
        AJ_CloseMsg(&msg);

        if ((status == AJ_ERR_READ) || (status == AJ_ERR_LINK_DEAD)) {
            AJ_InfoPrintf(("AllJoyn disconnect\n"));
            AJ_InfoPrintf(("Disconnected from Daemon:%s\n", AJ_GetUniqueName(&bus)));
            AJ_Disconnect(&bus);
            connected = FALSE;
            /*
             * Sleep a little while before trying to reconnect
             */
            AJ_Sleep(10 * 1000);
        }
    }
    AJ_WarnPrintf(("svclite EXIT %d\n", status));

    return status;
}
示例#5
0
AJ_Status AJS_MessageLoop(duk_context* ctx, AJ_BusAttachment* aj, duk_idx_t ajIdx)
{
    AJ_Status status = AJ_OK;
    AJ_Message msg;
    AJ_Time timerClock;
    uint32_t linkTO;
    uint32_t msgTO = 0x7FFFFFFF;
    duk_idx_t top = duk_get_top_index(ctx);
    uint8_t ldstate;

    AJ_InfoPrintf(("AJS_MessageLoop top=%d\n", (int)top));

    deferredOp = AJS_OP_NONE;

    if (ajIdx >= 0) {
        /*
         * Read the link timeout property from the config set
         */
        duk_get_prop_string(ctx, -1, "config");
        duk_get_prop_string(ctx, -1, "linkTimeout");
        linkTO = duk_get_int(ctx, -1);
        duk_pop_2(ctx);
        AJ_SetBusLinkTimeout(aj, linkTO);
    }
    /*
     * timer clock must be initialized
     */
    AJ_InitTimer(&timerClock);

    AJ_ASSERT(duk_get_top_index(ctx) == top);

    /*
     * Initialize About we can start sending announcements
     */
    AJ_AboutInit(aj, AJS_APP_PORT);

    while (status == AJ_OK) {
        /*
         * Check we are cleaning up the duktape stack correctly.
         */
        if (duk_get_top_index(ctx) != top) {
            AJ_ErrPrintf(("!!!AJS_MessageLoop top=%d expected %d\n", (int)duk_get_top_index(ctx), (int)top));
            AJS_DumpStack(ctx);
            AJ_ASSERT(duk_get_top_index(ctx) == top);
        }
        AJS_SetWatchdogTimer(AJS_DEFAULT_WATCHDOG_TIMEOUT);
        /*
         * Pinned items (strings/buffers) are only valid while running script
         */
        AJS_ClearPins(ctx);
        /*
         * Check if there are any pending I/O operations to perform.
         */
        status = AJS_ServiceIO(ctx);
        if (status != AJ_OK) {
            AJ_ErrPrintf(("Error servicing I/O functions\n"));
            break;
        }
        /*
         * Services the internal and timeout timers and updates the timeout value for any new
         * timers that have been registered since this function was last called.
         */
        status = AJS_RunTimers(ctx, &timerClock, &msgTO);
        if (status != AJ_OK) {
            AJ_ErrPrintf(("Error servicing timer functions\n"));
            break;
        }
        /*
         * Do any announcing required
         */
        status = AJS_GetLockdownState(&ldstate);
        if (status == AJ_OK && ldstate == AJS_CONSOLE_UNLOCKED) {
            status = AJ_AboutAnnounce(aj);
        }
        if (status != AJ_OK) {
            break;
        }
        /*
         * This special wildcard allows us to unmarshal signals with any source path
         */
        AJS_SetObjectPath("!");
        /*
         * Block until a message is received, the timeout expires, or the operation is interrupted.
         */
        status = AJ_UnmarshalMsg(aj, &msg, msgTO);
        if (status != AJ_OK) {
            if ((status == AJ_ERR_INTERRUPTED) || (status == AJ_ERR_TIMEOUT)) {
                status = AJ_OK;
                continue;
            }
            if (status == AJ_ERR_NO_MATCH) {
                status = AJ_OK;
            }
            AJ_CloseMsg(&msg);
            continue;
        }

        switch (msg.msgId) {
        case 0:
            /* If a message was parsed but is unrecognized and should be ignored */
            break;

        /* Introspection messages */
        case AJ_METHOD_PING:
        case AJ_METHOD_BUS_PING:
        case AJ_METHOD_GET_MACHINE_ID:
        case AJ_METHOD_INTROSPECT:
        case AJ_METHOD_GET_DESCRIPTION_LANG:
        case AJ_METHOD_INTROSPECT_WITH_DESC:
        /* About messages */
        case AJ_METHOD_ABOUT_GET_PROP:
        case AJ_METHOD_ABOUT_SET_PROP:
        case AJ_METHOD_ABOUT_GET_ABOUT_DATA:
        case AJ_METHOD_ABOUT_GET_OBJECT_DESCRIPTION:
        case AJ_METHOD_ABOUT_ICON_GET_PROP:
        case AJ_METHOD_ABOUT_ICON_SET_PROP:
        case AJ_METHOD_ABOUT_ICON_GET_URL:
        case AJ_METHOD_ABOUT_ICON_GET_CONTENT:
        /* Authentication messages and replies */
        case AJ_METHOD_EXCHANGE_GUIDS:
        case AJ_REPLY_ID(AJ_METHOD_EXCHANGE_GUIDS):
        case AJ_METHOD_EXCHANGE_SUITES:
        case AJ_REPLY_ID(AJ_METHOD_EXCHANGE_SUITES):
        case AJ_METHOD_AUTH_CHALLENGE:
        case AJ_REPLY_ID(AJ_METHOD_AUTH_CHALLENGE):
        case AJ_METHOD_GEN_SESSION_KEY:
        case AJ_REPLY_ID(AJ_METHOD_GEN_SESSION_KEY):
        case AJ_METHOD_EXCHANGE_GROUP_KEYS:
        case AJ_REPLY_ID(AJ_METHOD_EXCHANGE_GROUP_KEYS):
        case AJ_METHOD_KEY_EXCHANGE:
        case AJ_REPLY_ID(AJ_METHOD_KEY_EXCHANGE):
        case AJ_METHOD_KEY_AUTHENTICATION:
        case AJ_REPLY_ID(AJ_METHOD_KEY_AUTHENTICATION):
        /* Replies the app ignores */
        case AJ_REPLY_ID(AJ_METHOD_ADD_MATCH):
        case AJ_REPLY_ID(AJ_METHOD_REMOVE_MATCH):
        case AJ_REPLY_ID(AJ_METHOD_PING):
        case AJ_REPLY_ID(AJ_METHOD_BUS_PING):
        /* Signals the app ignores */
        case AJ_SIGNAL_PROBE_ACK:
        case AJ_SIGNAL_PROBE_REQ:
        case AJ_SIGNAL_NAME_OWNER_CHANGED:
            status = AJ_BusHandleBusMessage(&msg);
            break;

        case AJ_METHOD_ACCEPT_SESSION:
            status = SessionDispatcher(ctx, &msg);
            break;

        case AJ_REPLY_ID(AJ_METHOD_BIND_SESSION_PORT):
            status = SessionBindReply(ctx, &msg);
            break;

        default:
            status = HandleMessage(ctx, ajIdx, &msg);
            break;
        }
        /*
         * Free message resources
         */
        AJ_CloseMsg(&msg);
        /*
         * Decide which messages should cause us to exit
         */
        switch (status) {
        case AJ_OK:
            break;

        case AJ_ERR_READ:
        case AJ_ERR_WRITE:
        case AJ_ERR_RESTART:
        case AJ_ERR_RESTART_APP:
            break;

        default:
            AJ_ErrPrintf(("Got error %s - continuing anyway\n", AJ_StatusText(status)));
            status = AJ_OK;
        }
        /*
         * Let link monitor know we are getting messages
         */
        AJ_NotifyLinkActive();
        /*
         * Perform any deferred operations. These are operations such as factory reset that cannot
         * be cleanly performed from inside duktape.
         */
        if (status == AJ_OK) {
            status = DoDeferredOperation(ctx);
        }
    }
    AJS_ClearPins(ctx);
    AJS_ClearWatchdogTimer();
    return status;
}