⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 gupnp-service-proxy.c

📁 另一 UPNP SDK 支持在UNIX/LINUX上运行。 UPnP是一种网络协议
💻 C
📖 第 1 页 / 共 5 页
字号:
 * parameter value, followed by %NULL, and then tuples of out paramater name, * out parameter type, and out parameter value location * * See gupnp_service_proxy_send_action(); this version takes a va_list for * use by language bindings. * * Return value: %TRUE if sending the action was succesful. **/gbooleangupnp_service_proxy_send_action_valist (GUPnPServiceProxy *proxy,                                        const char        *action,                                        GError           **error,                                        va_list            var_args){        GUPnPContext *context;        GMainContext *main_context;        GMainLoop *main_loop;        GUPnPServiceProxyAction *handle;        g_return_val_if_fail (GUPNP_IS_SERVICE_PROXY (proxy), FALSE);        g_return_val_if_fail (action, FALSE);        context = gupnp_service_info_get_context (GUPNP_SERVICE_INFO (proxy));        main_context = gssdp_client_get_main_context (GSSDP_CLIENT (context));        main_loop = g_main_loop_new (main_context, TRUE);        handle = gupnp_service_proxy_begin_action_valist (proxy,                                                          action,                                                          stop_main_loop,                                                          main_loop,                                                          var_args);        /* Loop till we get a reply (or time out) */        if (g_main_loop_is_running (main_loop))                g_main_loop_run (main_loop);        g_main_loop_unref (main_loop);        if (!gupnp_service_proxy_end_action_valist (proxy,                                                    handle,                                                    error,                                                    handle->var_args))                return FALSE;        return TRUE;}/** * gupnp_service_proxy_send_action_hash * @proxy: A #GUPnPServiceProxy * @action: An action * @error: The location where to store any error, or %NULL * @in_hash: A #GHashTable of in parameter name and #GValue pairs * @out_hash: A #GHashTable of out parameter name and initialized * #GValue pairs * * See gupnp_service_proxy_send_action(); this version takes a pair of * #GHashTable<!-- -->s for runtime determined parameter lists. * * Return value: %TRUE if sending the action was succesful. **/gbooleangupnp_service_proxy_send_action_hash (GUPnPServiceProxy *proxy,                                      const char        *action,                                      GError           **error,                                      GHashTable        *in_hash,                                      GHashTable        *out_hash){        GUPnPContext *context;        GMainContext *main_context;        GMainLoop *main_loop;        GUPnPServiceProxyAction *handle;        g_return_val_if_fail (GUPNP_IS_SERVICE_PROXY (proxy), FALSE);        g_return_val_if_fail (action, FALSE);        context = gupnp_service_info_get_context (GUPNP_SERVICE_INFO (proxy));        main_context = gssdp_client_get_main_context (GSSDP_CLIENT (context));        main_loop = g_main_loop_new (main_context, TRUE);        handle = gupnp_service_proxy_begin_action_hash (proxy,                                                        action,                                                        stop_main_loop,                                                        main_loop,                                                        in_hash);        if (!handle) {                g_main_loop_unref (main_loop);                return FALSE;        }        /* Loop till we get a reply (or time out) */        if (g_main_loop_is_running (main_loop))                g_main_loop_run (main_loop);        g_main_loop_unref (main_loop);        if (!gupnp_service_proxy_end_action_hash (proxy,                                                  handle,                                                  error,                                                  out_hash))                return FALSE;        return TRUE;}/** * gupnp_service_proxy_begin_action * @proxy: A #GUPnPServiceProxy * @action: An action * @callback: The callback to call when sending the action has succeeded * or failed * @user_data: User data for @callback * @Varargs: tuples of in parameter name, in paramater type, and in parameter * value, terminated with %NULL * * Sends action @action with parameters @Varargs to the service exposed by * @proxy asynchronously, calling @callback on completion. From @callback, call * gupnp_service_proxy_end_action() to check for errors, to retrieve return * values, and to free the #GUPnPServiceProxyAction. * * Return value: A #GUPnPServiceProxyAction handle. This will * be freed when calling gupnp_service_proxy_cancel_action() or * gupnp_service_proxy_end_action_valist(). **/GUPnPServiceProxyAction *gupnp_service_proxy_begin_action (GUPnPServiceProxy              *proxy,                                  const char                     *action,                                  GUPnPServiceProxyActionCallback callback,                                  gpointer                        user_data,                                  ...){        va_list var_args;        GUPnPServiceProxyAction *ret;        va_start (var_args, user_data);        ret = gupnp_service_proxy_begin_action_valist (proxy,                                                       action,                                                       callback,                                                       user_data,                                                       var_args);        va_end (var_args);        return ret;}/* Begins a basic action message */static GUPnPServiceProxyAction *begin_action_msg (GUPnPServiceProxy              *proxy,                  const char                     *action,                  GUPnPServiceProxyActionCallback callback,                  gpointer                        user_data){        GUPnPServiceProxyAction *ret;        char *control_url, *full_action;        const char *service_type;        /* Create action structure */        ret = g_slice_new (GUPnPServiceProxyAction);        ret->proxy = proxy;        ret->callback  = callback;        ret->user_data = user_data;        ret->msg = NULL;        ret->error = NULL;        proxy->priv->pending_actions =                g_list_prepend (proxy->priv->pending_actions, ret);        /* Make sure we have a service type */        service_type = gupnp_service_info_get_service_type                                        (GUPNP_SERVICE_INFO (proxy));        if (service_type == NULL) {                ret->error = g_error_new (GUPNP_SERVER_ERROR,                                          GUPNP_SERVER_ERROR_OTHER,                                          "No service type defined");                return ret;        }        /* Create message */        control_url = gupnp_service_info_get_control_url                                        (GUPNP_SERVICE_INFO (proxy));        if (control_url != NULL) {                ret->msg = soup_message_new (SOUP_METHOD_POST, control_url);                g_free (control_url);        }        if (ret->msg == NULL) {                ret->error = g_error_new (GUPNP_SERVER_ERROR,                                          GUPNP_SERVER_ERROR_INVALID_URL,                                          "No valid control URL defined");                return ret;        }        /* Specify action */        full_action = g_strdup_printf ("\"%s#%s\"", service_type, action);        soup_message_headers_append (ret->msg->request_headers,				     "SOAPAction",                                     full_action);        g_free (full_action);        /* Specify user agent and language */        http_request_set_user_agent (ret->msg);        http_request_set_accept_language (ret->msg);        /* Set up envelope */        ret->msg_str = xml_util_new_string ();        g_string_append (ret->msg_str,                         "<?xml version=\"1.0\"?>"                         "<s:Envelope xmlns:s="                                "\"http://schemas.xmlsoap.org/soap/envelope/\" "                          "s:encodingStyle="                                "\"http://schemas.xmlsoap.org/soap/encoding/\">"                         "<s:Body>");        g_string_append (ret->msg_str, "<u:");        g_string_append (ret->msg_str, action);        g_string_append (ret->msg_str, " xmlns:u=\"");        g_string_append (ret->msg_str, service_type);        g_string_append (ret->msg_str, "\">");        return ret;}/* Received response to action message */static voidaction_got_response (SoupSession             *session,                     SoupMessage             *msg,                     GUPnPServiceProxyAction *action){        const char *full_action;        switch (msg->status_code) {        case SOUP_STATUS_CANCELLED:                /* Silently return */                break;        case SOUP_STATUS_METHOD_NOT_ALLOWED:                /* Retry with M-POST */                msg->method = "M-POST";                soup_message_headers_append                        (msg->request_headers,                         "Man",                         "\"http://schemas.xmlsoap.org/soap/envelope/\"; ns=s");                /* Rename "SOAPAction" to "s-SOAPAction" */                full_action = soup_message_headers_get (msg->request_headers,                                                        "SOAPAction");                soup_message_headers_append (msg->request_headers,                                             "s-SOAPAction",                                             full_action);                soup_message_headers_remove (msg->request_headers,                                            "SOAPAction");                /* And re-queue */                soup_session_requeue_message (session, msg);                break;        default:                /* Success: Call callback */                action->callback (action->proxy, action, action->user_data);                break;        }}/* Finishes an action message and sends it off */static voidfinish_action_msg (GUPnPServiceProxyAction *action,                   const char              *action_name){        GUPnPContext *context;        SoupSession *session;        /* Finish message */        g_string_append (action->msg_str, "</u:");        g_string_append (action->msg_str, action_name);        g_string_append_c (action->msg_str, '>');        g_string_append (action->msg_str,                         "</s:Body>"                         "</s:Envelope>");        soup_message_set_request (action->msg,                                  "text/xml",                                  SOUP_MEMORY_TAKE,                                  action->msg_str->str,                                  action->msg_str->len);        g_string_free (action->msg_str, FALSE);        /* We need to keep our own reference to the message as well,         * in order for send_action() to work. */        g_object_ref (action->msg);        /* Send the message */        context = gupnp_service_info_get_context                                (GUPNP_SERVICE_INFO (action->proxy));        session = _gupnp_context_get_session (context);        soup_session_queue_message (session,                                    action->msg,                                    (SoupSessionCallback) action_got_response,                                    action);}/* Writes a parameter name and GValue pair to @msg */static voidwrite_in_parameter (const char *arg_name,                    GValue     *value,                    GString    *msg_str){        /* Write parameter pair */        xml_util_start_element (msg_str, arg_name);        gvalue_util_value_append_to_xml_string (value, msg_str);        xml_util_end_element (msg_str, arg_name);}/** * gupnp_service_proxy_begin_action_valist * @proxy: A #GUPnPServiceProxy * @action: An action * @callback: The callback to call when sending the action has succeeded * or failed * @user_data: User data for @callback * @var_args: A va_list of tuples of in parameter name, in paramater type, and * in parameter value * * See gupnp_service_proxy_begin_action(); this version takes a va_list for * use by language bindings. * * Return value: A #GUPnPServiceProxyAction handle. This will * be freed when calling gupnp_service_proxy_cancel_action() or * gupnp_service_proxy_end_action_valist(). **/GUPnPServiceProxyAction *gupnp_service_proxy_begin_action_valist                                   (GUPnPServiceProxy              *proxy,                                    const char                     *action,                                    GUPnPServiceProxyActionCallback callback,                                    gpointer                        user_data,                                    va_list                         var_args){        const char *arg_name;        GUPnPServiceProxyAction *ret;        g_return_val_if_fail (GUPNP_IS_SERVICE_PROXY (proxy), NULL);        g_return_val_if_fail (action, NULL);        g_return_val_if_fail (callback, NULL);        /* Create message */        ret = begin_action_msg (proxy, action, callback, user_data);        if (ret->error) {                callback (proxy, ret, user_data);                return ret;        }        /* Arguments */        arg_name = va_arg (var_args, const char *);        while (arg_name) {                GType arg_type;                GValue value = { 0, };                char *collect_error = NULL;                arg_type = va_arg (var_args, GType);                g_value_init (&value, arg_type);                G_VALUE_COLLECT (&value, var_args, 0, &collect_error);                if (!collect_error) {                        write_in_parameter (arg_name, &value, ret->msg_str);                        g_value_unset (&value);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -