2013-04-23 07:40:05 -07:00
|
|
|
#include "eldbus_private.h"
|
|
|
|
#include "eldbus_private_types.h"
|
2012-09-17 13:41:05 -07:00
|
|
|
#include <dbus/dbus.h>
|
|
|
|
#include <stdint.h>
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
/* TODO: mempool of Eldbus_Message and Eldbus_Message_Iter */
|
2012-09-17 13:41:05 -07:00
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
#define ELDBUS_MESSAGE_CHECK(msg) \
|
2012-09-17 13:41:05 -07:00
|
|
|
do \
|
|
|
|
{ \
|
|
|
|
EINA_SAFETY_ON_NULL_RETURN(msg); \
|
2013-04-23 07:40:05 -07:00
|
|
|
if (!EINA_MAGIC_CHECK(msg, ELDBUS_MESSAGE_MAGIC)) \
|
2012-09-17 13:41:05 -07:00
|
|
|
{ \
|
2013-04-23 07:40:05 -07:00
|
|
|
EINA_MAGIC_FAIL(msg, ELDBUS_MESSAGE_MAGIC); \
|
2012-09-17 13:41:05 -07:00
|
|
|
return; \
|
|
|
|
} \
|
|
|
|
EINA_SAFETY_ON_TRUE_RETURN(msg->refcount <= 0); \
|
|
|
|
} \
|
|
|
|
while (0)
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
#define ELDBUS_MESSAGE_CHECK_RETVAL(msg, retval) \
|
2012-09-17 13:41:05 -07:00
|
|
|
do \
|
|
|
|
{ \
|
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(msg, retval); \
|
2013-04-23 07:40:05 -07:00
|
|
|
if (!EINA_MAGIC_CHECK(msg, ELDBUS_MESSAGE_MAGIC)) \
|
2012-09-17 13:41:05 -07:00
|
|
|
{ \
|
2013-04-23 07:40:05 -07:00
|
|
|
EINA_MAGIC_FAIL(msg, ELDBUS_MESSAGE_MAGIC); \
|
2012-09-17 13:41:05 -07:00
|
|
|
return retval; \
|
|
|
|
} \
|
|
|
|
EINA_SAFETY_ON_TRUE_RETURN_VAL(msg->refcount <= 0, retval); \
|
|
|
|
} \
|
|
|
|
while (0)
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
#define ELDBUS_MESSAGE_ITERATOR_CHECK(iter) \
|
2012-09-17 13:41:05 -07:00
|
|
|
do \
|
|
|
|
{ \
|
|
|
|
EINA_SAFETY_ON_NULL_RETURN(iter); \
|
2013-04-23 07:40:05 -07:00
|
|
|
if (!EINA_MAGIC_CHECK(iter, ELDBUS_MESSAGE_ITERATOR_MAGIC)) \
|
2012-09-17 13:41:05 -07:00
|
|
|
{ \
|
2013-04-23 07:40:05 -07:00
|
|
|
EINA_MAGIC_FAIL(iter, ELDBUS_MESSAGE_ITERATOR_MAGIC); \
|
2012-09-17 13:41:05 -07:00
|
|
|
return; \
|
|
|
|
} \
|
|
|
|
} \
|
|
|
|
while (0)
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
#define ELDBUS_MESSAGE_ITERATOR_CHECK_RETVAL(iter, retval) \
|
2012-09-17 13:41:05 -07:00
|
|
|
do \
|
|
|
|
{ \
|
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(iter, retval); \
|
2013-04-23 07:40:05 -07:00
|
|
|
if (!EINA_MAGIC_CHECK(iter, ELDBUS_MESSAGE_ITERATOR_MAGIC)) \
|
2012-09-17 13:41:05 -07:00
|
|
|
{ \
|
2013-04-23 07:40:05 -07:00
|
|
|
EINA_MAGIC_FAIL(iter, ELDBUS_MESSAGE_ITERATOR_MAGIC); \
|
2012-09-17 13:41:05 -07:00
|
|
|
return retval; \
|
|
|
|
} \
|
|
|
|
} \
|
|
|
|
while (0)
|
|
|
|
|
|
|
|
static Eina_Bool append_basic(char type, va_list *vl, DBusMessageIter *iter);
|
|
|
|
|
|
|
|
Eina_Bool
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_init(void)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
|
|
|
return EINA_TRUE;
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_shutdown(void)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
|
|
|
}
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
static Eldbus_Message_Iter *
|
2012-09-17 13:41:05 -07:00
|
|
|
_message_iterator_new(Eina_Bool writable)
|
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
Eldbus_Message_Iter *iter;
|
2012-09-17 13:41:05 -07:00
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
iter = calloc(1, sizeof(Eldbus_Message_Iter));
|
2012-09-17 13:41:05 -07:00
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(iter, NULL);
|
2013-04-23 07:40:05 -07:00
|
|
|
EINA_MAGIC_SET(iter, ELDBUS_MESSAGE_ITERATOR_MAGIC);
|
2012-09-17 13:41:05 -07:00
|
|
|
iter->writable = writable;
|
|
|
|
|
|
|
|
return iter;
|
|
|
|
}
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
Eldbus_Message *eldbus_message_new(Eina_Bool writable)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
Eldbus_Message *msg = calloc(1, sizeof(Eldbus_Message));
|
2012-09-17 13:41:05 -07:00
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(msg, NULL);
|
2013-04-23 07:40:05 -07:00
|
|
|
EINA_MAGIC_SET(msg, ELDBUS_MESSAGE_MAGIC);
|
2012-09-17 13:41:05 -07:00
|
|
|
msg->refcount = 1;
|
|
|
|
|
|
|
|
msg->iterator = _message_iterator_new(writable);
|
|
|
|
EINA_SAFETY_ON_NULL_GOTO(msg->iterator, fail);
|
|
|
|
|
|
|
|
return msg;
|
|
|
|
|
|
|
|
fail:
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_unref(msg);
|
2012-09-17 13:41:05 -07:00
|
|
|
return NULL;
|
|
|
|
}
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
EAPI Eldbus_Message *
|
|
|
|
eldbus_message_method_call_new(const char *dest, const char *path, const char *iface, const char *method)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
Eldbus_Message *msg;
|
2012-09-17 13:41:05 -07:00
|
|
|
|
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(dest, NULL);
|
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(path, NULL);
|
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(iface, NULL);
|
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(method, NULL);
|
|
|
|
|
2015-10-05 19:29:16 -07:00
|
|
|
#ifdef DBUS_SYNTAX_H
|
|
|
|
// added to libdbus:
|
|
|
|
// f426c6cddd158d6324923f28117bc8e512d6f64f Fri Feb 24 12:43:55 2012 +0000
|
2015-10-04 01:53:46 -07:00
|
|
|
if (!dbus_validate_bus_name(dest, NULL))
|
|
|
|
{
|
|
|
|
ERR("Invalid bus name '%s'", dest);
|
|
|
|
return NULL;
|
|
|
|
}
|
|
|
|
if (!dbus_validate_path(path, NULL))
|
|
|
|
{
|
|
|
|
ERR("Invalid path '%s'", path);
|
|
|
|
return NULL;
|
|
|
|
}
|
|
|
|
if (!dbus_validate_interface(iface, NULL))
|
|
|
|
{
|
|
|
|
ERR("Invalid interface '%s'", iface);
|
|
|
|
return NULL;
|
|
|
|
}
|
2015-10-05 19:29:16 -07:00
|
|
|
#endif
|
2015-10-04 01:53:46 -07:00
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
msg = eldbus_message_new(EINA_TRUE);
|
2012-09-17 13:41:05 -07:00
|
|
|
EINA_SAFETY_ON_NULL_GOTO(msg, fail);
|
|
|
|
|
|
|
|
msg->dbus_msg = dbus_message_new_method_call(dest, path, iface, method);
|
|
|
|
dbus_message_iter_init_append(msg->dbus_msg, &msg->iterator->dbus_iterator);
|
|
|
|
|
|
|
|
return msg;
|
|
|
|
|
|
|
|
fail:
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_unref(msg);
|
2012-09-17 13:41:05 -07:00
|
|
|
return NULL;
|
|
|
|
}
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
EAPI Eldbus_Message *
|
|
|
|
eldbus_message_ref(Eldbus_Message *msg)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_CHECK_RETVAL(msg, NULL);
|
2012-09-17 13:41:05 -07:00
|
|
|
DBG("msg=%p, pre-refcount=%d", msg, msg->refcount);
|
|
|
|
msg->refcount++;
|
|
|
|
return msg;
|
|
|
|
}
|
|
|
|
|
|
|
|
static void
|
2013-04-23 07:40:05 -07:00
|
|
|
_message_iterator_free(Eldbus_Message_Iter *iter)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
|
|
|
Eina_Inlist *lst, *next;
|
2013-04-23 07:40:05 -07:00
|
|
|
Eldbus_Message_Iter *sub;
|
2012-09-17 13:41:05 -07:00
|
|
|
if (!iter) return;
|
|
|
|
|
|
|
|
lst = iter->iterators;
|
|
|
|
while (lst)
|
|
|
|
{
|
|
|
|
next = lst->next;
|
2013-04-23 07:40:05 -07:00
|
|
|
sub = EINA_INLIST_CONTAINER_GET(lst, Eldbus_Message_Iter);
|
2012-09-17 13:41:05 -07:00
|
|
|
_message_iterator_free(sub);
|
|
|
|
lst = next;
|
|
|
|
}
|
|
|
|
free(iter);
|
|
|
|
}
|
|
|
|
|
|
|
|
EAPI void
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_unref(Eldbus_Message *msg)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_CHECK(msg);
|
2012-09-17 13:41:05 -07:00
|
|
|
DBG("msg=%p, pre-refcount=%d", msg, msg->refcount);
|
|
|
|
msg->refcount--;
|
|
|
|
if (msg->refcount > 0) return;
|
|
|
|
|
|
|
|
DBG("message free %p", msg);
|
|
|
|
|
|
|
|
EINA_MAGIC_SET(msg, EINA_MAGIC_NONE);
|
|
|
|
if (msg->dbus_msg)
|
|
|
|
dbus_message_unref(msg->dbus_msg);
|
|
|
|
msg->dbus_msg = NULL;
|
|
|
|
|
|
|
|
_message_iterator_free(msg->iterator);
|
|
|
|
free(msg);
|
|
|
|
}
|
|
|
|
|
|
|
|
EAPI const char *
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_path_get(const Eldbus_Message *msg)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_CHECK_RETVAL(msg, NULL);
|
2012-09-17 13:41:05 -07:00
|
|
|
return dbus_message_get_path(msg->dbus_msg);
|
|
|
|
}
|
|
|
|
|
|
|
|
EAPI const char *
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_interface_get(const Eldbus_Message *msg)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_CHECK_RETVAL(msg, NULL);
|
2012-09-17 13:41:05 -07:00
|
|
|
return dbus_message_get_interface(msg->dbus_msg);
|
|
|
|
}
|
|
|
|
|
|
|
|
EAPI const char *
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_member_get(const Eldbus_Message *msg)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_CHECK_RETVAL(msg, NULL);
|
2012-09-17 13:41:05 -07:00
|
|
|
return dbus_message_get_member(msg->dbus_msg);
|
|
|
|
}
|
|
|
|
|
|
|
|
EAPI const char *
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_destination_get(const Eldbus_Message *msg)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_CHECK_RETVAL(msg, NULL);
|
2012-09-17 13:41:05 -07:00
|
|
|
return dbus_message_get_destination(msg->dbus_msg);
|
|
|
|
}
|
|
|
|
|
|
|
|
EAPI const char *
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_sender_get(const Eldbus_Message *msg)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_CHECK_RETVAL(msg, NULL);
|
2012-09-17 13:41:05 -07:00
|
|
|
return dbus_message_get_sender(msg->dbus_msg);
|
|
|
|
}
|
|
|
|
|
|
|
|
EAPI const char *
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_signature_get(const Eldbus_Message *msg)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_CHECK_RETVAL(msg, NULL);
|
2012-09-17 13:41:05 -07:00
|
|
|
return dbus_message_get_signature(msg->dbus_msg);
|
|
|
|
}
|
|
|
|
|
|
|
|
EAPI Eina_Bool
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_error_get(const Eldbus_Message *msg, const char **name, const char **text)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
|
|
|
if (name) *name = NULL;
|
|
|
|
if (text) *text = NULL;
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_CHECK_RETVAL(msg, EINA_FALSE);
|
2012-09-17 13:41:05 -07:00
|
|
|
|
|
|
|
if (dbus_message_get_type(msg->dbus_msg) != DBUS_MESSAGE_TYPE_ERROR)
|
|
|
|
return EINA_FALSE;
|
|
|
|
|
|
|
|
if (name)
|
|
|
|
*name = dbus_message_get_error_name(msg->dbus_msg);
|
|
|
|
|
|
|
|
if (text)
|
|
|
|
dbus_message_get_args(msg->dbus_msg, NULL, DBUS_TYPE_STRING, text,
|
|
|
|
DBUS_TYPE_INVALID);
|
|
|
|
|
|
|
|
return EINA_TRUE;
|
|
|
|
}
|
|
|
|
|
|
|
|
static Eina_Bool
|
2013-04-23 07:40:05 -07:00
|
|
|
_eldbus_message_arguments_vget(Eldbus_Message *msg, const char *signature, va_list ap)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
Eldbus_Message_Iter *iter;
|
|
|
|
iter = eldbus_message_iter_get(msg);
|
|
|
|
ELDBUS_MESSAGE_ITERATOR_CHECK_RETVAL(iter, EINA_FALSE);
|
2012-09-17 13:41:05 -07:00
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
return eldbus_message_iter_arguments_vget(iter, signature, ap);
|
2012-09-17 13:41:05 -07:00
|
|
|
}
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
EAPI Eldbus_Message_Iter *
|
|
|
|
eldbus_message_iter_get(const Eldbus_Message *msg)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_CHECK_RETVAL(msg, NULL);
|
2012-09-17 13:41:05 -07:00
|
|
|
/* Something went wrong, msg->iterator should not be NULL */
|
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(msg->iterator, NULL);
|
|
|
|
|
|
|
|
return msg->iterator;
|
|
|
|
}
|
|
|
|
|
|
|
|
EAPI Eina_Bool
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_arguments_get(const Eldbus_Message *msg, const char *signature, ...)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
|
|
|
Eina_Bool ret;
|
|
|
|
va_list ap;
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_CHECK_RETVAL(msg, EINA_FALSE);
|
2012-09-17 13:41:05 -07:00
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(signature, EINA_FALSE);
|
|
|
|
|
|
|
|
va_start(ap, signature);
|
2013-04-23 07:40:05 -07:00
|
|
|
ret = _eldbus_message_arguments_vget((Eldbus_Message *)msg, signature, ap);
|
2012-09-17 13:41:05 -07:00
|
|
|
va_end(ap);
|
|
|
|
return ret;
|
|
|
|
}
|
|
|
|
|
|
|
|
EAPI Eina_Bool
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_arguments_vget(const Eldbus_Message *msg, const char *signature, va_list ap)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_CHECK_RETVAL(msg, EINA_FALSE);
|
2012-09-17 13:41:05 -07:00
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(signature, EINA_FALSE);
|
2013-04-23 07:40:05 -07:00
|
|
|
return _eldbus_message_arguments_vget((Eldbus_Message *)msg, signature, ap);
|
2012-09-17 13:41:05 -07:00
|
|
|
}
|
|
|
|
|
2013-01-02 12:55:57 -08:00
|
|
|
static Eina_Bool
|
2013-04-23 07:40:05 -07:00
|
|
|
_eldbus_message_iter_arguments_vappend(Eldbus_Message_Iter *iter, const char *signature, va_list *aq)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
|
|
|
DBusSignatureIter signature_iter;
|
|
|
|
Eina_Bool r = EINA_TRUE;
|
|
|
|
char *type;
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_ITERATOR_CHECK_RETVAL(iter, EINA_FALSE);
|
2012-09-17 13:41:05 -07:00
|
|
|
EINA_SAFETY_ON_FALSE_RETURN_VAL(iter->writable, EINA_FALSE);
|
2012-10-26 11:20:19 -07:00
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(signature, EINA_FALSE);
|
2012-09-17 13:41:05 -07:00
|
|
|
|
|
|
|
dbus_signature_iter_init(&signature_iter, signature);
|
2012-10-26 11:19:57 -07:00
|
|
|
while ((type = dbus_signature_iter_get_signature(&signature_iter)))
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
|
|
|
if (type[0] != DBUS_TYPE_VARIANT && !type[1])
|
2013-01-02 12:55:57 -08:00
|
|
|
r = append_basic(type[0], aq, &iter->dbus_iterator);
|
2012-09-17 13:41:05 -07:00
|
|
|
else
|
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
Eldbus_Message_Iter **user_itr;
|
|
|
|
Eldbus_Message_Iter *sub;
|
2012-09-17 13:41:05 -07:00
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
user_itr = va_arg(*aq, Eldbus_Message_Iter **);
|
2012-09-17 13:41:05 -07:00
|
|
|
sub = _message_iterator_new(EINA_TRUE);
|
2012-12-17 10:25:00 -08:00
|
|
|
if (!sub)
|
|
|
|
{
|
|
|
|
ERR("Could not create sub iterator");
|
|
|
|
r = EINA_FALSE;
|
|
|
|
goto next;
|
|
|
|
}
|
|
|
|
|
2012-09-17 13:41:05 -07:00
|
|
|
iter->iterators = eina_inlist_append(iter->iterators,
|
|
|
|
EINA_INLIST_GET(sub));
|
|
|
|
|
|
|
|
if (type[0] == DBUS_TYPE_ARRAY)
|
|
|
|
r = dbus_message_iter_open_container(&iter->dbus_iterator,
|
|
|
|
type[0], type+1,
|
|
|
|
&sub->dbus_iterator);
|
2012-12-17 10:25:06 -08:00
|
|
|
else if (type[1] == DBUS_TYPE_VARIANT)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
|
|
|
ERR("variant not supported by \
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_iter_arguments_append(), \
|
|
|
|
try eldbus_message_iter_container_new()");
|
2012-12-17 10:25:00 -08:00
|
|
|
r = EINA_FALSE;
|
|
|
|
goto next;
|
2012-09-17 13:41:05 -07:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
char real_type;
|
|
|
|
|
|
|
|
if (type[0] == DBUS_STRUCT_BEGIN_CHAR)
|
|
|
|
real_type = DBUS_TYPE_STRUCT;
|
|
|
|
else real_type = DBUS_TYPE_DICT_ENTRY;
|
|
|
|
r = dbus_message_iter_open_container(&iter->dbus_iterator,
|
|
|
|
real_type, NULL,
|
|
|
|
&sub->dbus_iterator);
|
|
|
|
}
|
|
|
|
*user_itr = sub;
|
|
|
|
}
|
|
|
|
|
2012-12-17 10:25:00 -08:00
|
|
|
next:
|
2012-09-17 13:41:05 -07:00
|
|
|
dbus_free(type);
|
2012-12-17 10:25:00 -08:00
|
|
|
if (!r || !dbus_signature_iter_next(&signature_iter))
|
|
|
|
break;
|
2012-09-17 13:41:05 -07:00
|
|
|
}
|
2012-12-17 10:25:00 -08:00
|
|
|
|
2012-09-17 13:41:05 -07:00
|
|
|
return r;
|
2013-01-02 12:55:57 -08:00
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
EAPI Eina_Bool
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_iter_arguments_vappend(Eldbus_Message_Iter *iter, const char *signature, va_list ap)
|
2013-01-02 12:55:57 -08:00
|
|
|
{
|
|
|
|
va_list aq;
|
|
|
|
Eina_Bool ret;
|
|
|
|
|
|
|
|
va_copy(aq, ap);
|
2013-04-23 07:40:05 -07:00
|
|
|
ret = _eldbus_message_iter_arguments_vappend(iter, signature, &aq);
|
2013-01-02 12:55:57 -08:00
|
|
|
va_end(aq);
|
|
|
|
|
|
|
|
return ret;
|
2012-09-17 13:41:05 -07:00
|
|
|
}
|
|
|
|
|
|
|
|
EAPI Eina_Bool
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_iter_arguments_append(Eldbus_Message_Iter *iter, const char *signature, ...)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
|
|
|
Eina_Bool r;
|
|
|
|
va_list ap;
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_ITERATOR_CHECK_RETVAL(iter, EINA_FALSE);
|
2012-09-17 13:41:05 -07:00
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(signature, EINA_FALSE);
|
|
|
|
|
|
|
|
va_start(ap, signature);
|
2013-04-23 07:40:05 -07:00
|
|
|
r = eldbus_message_iter_arguments_vappend(iter, signature, ap);
|
2012-09-17 13:41:05 -07:00
|
|
|
va_end(ap);
|
|
|
|
return r;
|
|
|
|
}
|
|
|
|
|
|
|
|
static Eina_Bool
|
|
|
|
append_basic(char type, va_list *vl, DBusMessageIter *iter)
|
|
|
|
{
|
|
|
|
switch (type)
|
|
|
|
{
|
|
|
|
case DBUS_TYPE_BYTE:
|
|
|
|
{
|
|
|
|
uint32_t read_byte = va_arg(*vl, uint32_t);
|
|
|
|
uint8_t byte = read_byte;
|
|
|
|
return dbus_message_iter_append_basic(iter, type, &byte);
|
|
|
|
}
|
|
|
|
case DBUS_TYPE_INT16:
|
|
|
|
{
|
|
|
|
int32_t read_int16 = va_arg(*vl, int32_t);
|
|
|
|
int16_t int16 = read_int16;
|
|
|
|
return dbus_message_iter_append_basic(iter, type, &int16);
|
|
|
|
}
|
|
|
|
case DBUS_TYPE_UINT16:
|
|
|
|
{
|
|
|
|
uint32_t read_uint16 = va_arg(*vl, uint32_t);
|
|
|
|
uint16_t uint16 = read_uint16;
|
|
|
|
return dbus_message_iter_append_basic(iter, type, &uint16);
|
|
|
|
}
|
|
|
|
case DBUS_TYPE_BOOLEAN:
|
|
|
|
case DBUS_TYPE_INT32:
|
2012-10-09 01:47:59 -07:00
|
|
|
#ifdef DBUS_TYPE_UNIX_FD
|
2012-09-17 13:41:05 -07:00
|
|
|
case DBUS_TYPE_UNIX_FD:
|
2012-10-09 01:47:59 -07:00
|
|
|
#endif
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
|
|
|
int32_t int32 = va_arg(*vl, int32_t);
|
|
|
|
return dbus_message_iter_append_basic(iter, type, &int32);
|
|
|
|
}
|
|
|
|
case DBUS_TYPE_UINT32:
|
|
|
|
{
|
|
|
|
uint32_t uint32 = va_arg(*vl, uint32_t);
|
|
|
|
return dbus_message_iter_append_basic(iter, type, &uint32);
|
|
|
|
}
|
|
|
|
case DBUS_TYPE_INT64:
|
|
|
|
{
|
|
|
|
int64_t int64 = va_arg(*vl, int64_t);
|
|
|
|
return dbus_message_iter_append_basic(iter, type, &int64);
|
|
|
|
}
|
|
|
|
case DBUS_TYPE_UINT64:
|
|
|
|
{
|
|
|
|
uint64_t uint64 = va_arg(*vl, uint64_t);
|
|
|
|
return dbus_message_iter_append_basic(iter, type, &uint64);
|
|
|
|
}
|
|
|
|
case DBUS_TYPE_DOUBLE:
|
|
|
|
{
|
|
|
|
double double_ieee = va_arg(*vl, double);
|
|
|
|
return dbus_message_iter_append_basic(iter, type, &double_ieee);
|
|
|
|
}
|
|
|
|
case DBUS_TYPE_STRING:
|
|
|
|
case DBUS_TYPE_OBJECT_PATH:
|
|
|
|
case DBUS_TYPE_SIGNATURE:
|
|
|
|
{
|
|
|
|
char *string = va_arg(*vl, char*);
|
|
|
|
return dbus_message_iter_append_basic(iter, type, &string);
|
|
|
|
}
|
|
|
|
default:
|
|
|
|
ERR("Type not handled %c", type);
|
|
|
|
return EINA_FALSE;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
static Eina_Bool
|
2013-04-23 07:40:05 -07:00
|
|
|
_eldbus_message_arguments_vappend(Eldbus_Message *msg, const char *signature, va_list *aq)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
|
|
|
DBusSignatureIter signature_iter;
|
2013-04-23 07:40:05 -07:00
|
|
|
Eldbus_Message_Iter *iter;
|
2012-12-17 10:24:54 -08:00
|
|
|
int type;
|
2012-09-17 13:41:05 -07:00
|
|
|
Eina_Bool r = EINA_TRUE;
|
|
|
|
|
2012-10-26 11:20:19 -07:00
|
|
|
if (!signature[0]) return EINA_TRUE;
|
|
|
|
EINA_SAFETY_ON_FALSE_RETURN_VAL(dbus_signature_validate(signature, NULL),
|
|
|
|
EINA_FALSE);
|
2012-09-17 13:41:05 -07:00
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
iter = eldbus_message_iter_get(msg);
|
2016-09-20 02:40:32 -07:00
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(iter, EINA_FALSE);
|
2012-09-17 13:41:05 -07:00
|
|
|
EINA_SAFETY_ON_FALSE_RETURN_VAL(iter->writable, EINA_FALSE);
|
|
|
|
|
|
|
|
dbus_signature_iter_init(&signature_iter, signature);
|
2012-12-17 10:24:54 -08:00
|
|
|
while ((type = dbus_signature_iter_get_current_type(&signature_iter)))
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2012-12-17 10:24:54 -08:00
|
|
|
if (dbus_type_is_basic(type))
|
2013-01-02 12:55:57 -08:00
|
|
|
r = append_basic(type, aq, &iter->dbus_iterator);
|
2012-09-17 13:41:05 -07:00
|
|
|
else
|
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
ERR("sig = %s | eldbus_message_arguments_append() and \
|
|
|
|
eldbus_message_arguments_vappend() only support basic types, \
|
|
|
|
to complex types use eldbus_message_iter_* functions",
|
2012-12-17 10:24:54 -08:00
|
|
|
signature);
|
2012-09-17 13:41:05 -07:00
|
|
|
r = EINA_FALSE;
|
|
|
|
}
|
|
|
|
|
2012-12-17 10:24:54 -08:00
|
|
|
if (!r || !dbus_signature_iter_next(&signature_iter))
|
|
|
|
break;
|
2012-09-17 13:41:05 -07:00
|
|
|
}
|
|
|
|
|
|
|
|
return r;
|
|
|
|
}
|
|
|
|
|
|
|
|
EAPI Eina_Bool
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_arguments_append(Eldbus_Message *msg, const char *signature, ...)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
|
|
|
Eina_Bool ret;
|
|
|
|
va_list ap;
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_CHECK_RETVAL(msg, EINA_FALSE);
|
2012-09-17 13:41:05 -07:00
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(signature, EINA_FALSE);
|
|
|
|
|
|
|
|
va_start(ap, signature);
|
2013-04-23 07:40:05 -07:00
|
|
|
ret = _eldbus_message_arguments_vappend(msg, signature, &ap);
|
2012-09-17 13:41:05 -07:00
|
|
|
va_end(ap);
|
|
|
|
return ret;
|
|
|
|
}
|
|
|
|
|
|
|
|
EAPI Eina_Bool
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_arguments_vappend(Eldbus_Message *msg, const char *signature, va_list ap)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-01-02 12:55:57 -08:00
|
|
|
va_list aq;
|
|
|
|
Eina_Bool ret;
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_CHECK_RETVAL(msg, EINA_FALSE);
|
2012-09-17 13:41:05 -07:00
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(signature, EINA_FALSE);
|
2013-01-02 12:55:57 -08:00
|
|
|
|
|
|
|
va_copy(aq, ap);
|
2013-04-23 07:40:05 -07:00
|
|
|
ret = _eldbus_message_arguments_vappend(msg, signature, &aq);
|
2013-01-02 12:55:57 -08:00
|
|
|
va_end(aq);
|
|
|
|
|
|
|
|
return ret;
|
2012-09-17 13:41:05 -07:00
|
|
|
}
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
EAPI Eldbus_Message_Iter *
|
|
|
|
eldbus_message_iter_container_new(Eldbus_Message_Iter *iter, int type, const char* contained_signature)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
Eldbus_Message_Iter *sub;
|
2012-09-17 13:41:05 -07:00
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_ITERATOR_CHECK_RETVAL(iter, NULL);
|
2012-09-17 13:41:05 -07:00
|
|
|
sub = _message_iterator_new(EINA_TRUE);
|
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(sub, NULL);
|
|
|
|
|
|
|
|
if (!dbus_message_iter_open_container(&iter->dbus_iterator, type,
|
|
|
|
contained_signature,
|
|
|
|
&sub->dbus_iterator))
|
|
|
|
goto cleanup;
|
|
|
|
|
|
|
|
iter->iterators = eina_inlist_append(iter->iterators, EINA_INLIST_GET(sub));
|
|
|
|
return sub;
|
|
|
|
|
|
|
|
cleanup:
|
|
|
|
free(sub);
|
|
|
|
return NULL;
|
|
|
|
}
|
|
|
|
|
|
|
|
EAPI Eina_Bool
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_iter_container_close(Eldbus_Message_Iter *iter, Eldbus_Message_Iter *sub)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_ITERATOR_CHECK_RETVAL(iter, EINA_FALSE);
|
|
|
|
ELDBUS_MESSAGE_ITERATOR_CHECK_RETVAL(sub, EINA_FALSE);
|
2012-09-17 13:41:05 -07:00
|
|
|
EINA_SAFETY_ON_FALSE_RETURN_VAL(iter->writable, EINA_FALSE);
|
|
|
|
return dbus_message_iter_close_container(&iter->dbus_iterator,
|
|
|
|
&sub->dbus_iterator);
|
|
|
|
}
|
|
|
|
|
|
|
|
EAPI Eina_Bool
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_iter_basic_append(Eldbus_Message_Iter *iter, int type, ...)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
|
|
|
Eina_Bool r;
|
|
|
|
va_list vl;
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_ITERATOR_CHECK_RETVAL(iter, EINA_FALSE);
|
2012-09-17 13:41:05 -07:00
|
|
|
EINA_SAFETY_ON_FALSE_RETURN_VAL(iter->writable, EINA_FALSE);
|
|
|
|
|
|
|
|
va_start(vl, type);
|
|
|
|
r = append_basic(type, &vl, &iter->dbus_iterator);
|
|
|
|
va_end(vl);
|
|
|
|
|
|
|
|
return r;
|
|
|
|
}
|
|
|
|
|
2013-03-22 20:24:23 -07:00
|
|
|
EAPI Eina_Bool
|
|
|
|
eldbus_message_iter_fixed_array_append(Eldbus_Message_Iter *iter, int type, const void *array, unsigned int size)
|
|
|
|
{
|
|
|
|
ELDBUS_MESSAGE_ITERATOR_CHECK_RETVAL(iter, EINA_FALSE);
|
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(array, EINA_FALSE);
|
|
|
|
EINA_SAFETY_ON_FALSE_RETURN_VAL(iter->writable, EINA_FALSE);
|
|
|
|
EINA_SAFETY_ON_FALSE_RETURN_VAL(dbus_type_is_basic(type), EINA_FALSE);
|
|
|
|
return dbus_message_iter_append_fixed_array(&iter->dbus_iterator, type, &array, (int)size);
|
|
|
|
}
|
|
|
|
|
2012-09-17 13:41:05 -07:00
|
|
|
EAPI void
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_iter_basic_get(Eldbus_Message_Iter *iter, void *value)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_ITERATOR_CHECK(iter);
|
2012-09-17 13:41:05 -07:00
|
|
|
EINA_SAFETY_ON_TRUE_RETURN(iter->writable);
|
|
|
|
dbus_message_iter_get_basic(&iter->dbus_iterator, value);
|
|
|
|
}
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
Eldbus_Message_Iter *
|
|
|
|
eldbus_message_iter_sub_iter_get(Eldbus_Message_Iter *iter)
|
2012-10-18 13:11:10 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
Eldbus_Message_Iter *sub;
|
|
|
|
ELDBUS_MESSAGE_ITERATOR_CHECK_RETVAL(iter, NULL);
|
2012-10-18 13:11:10 -07:00
|
|
|
EINA_SAFETY_ON_TRUE_RETURN_VAL(iter->writable, NULL);
|
|
|
|
|
|
|
|
sub = _message_iterator_new(EINA_FALSE);
|
|
|
|
dbus_message_iter_recurse(&iter->dbus_iterator, &sub->dbus_iterator);
|
|
|
|
iter->iterators = eina_inlist_append(iter->iterators,
|
|
|
|
EINA_INLIST_GET(sub));
|
|
|
|
return sub;
|
|
|
|
}
|
|
|
|
|
2012-10-26 11:20:19 -07:00
|
|
|
EAPI char *
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_iter_signature_get(Eldbus_Message_Iter *iter)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_ITERATOR_CHECK_RETVAL(iter, NULL);
|
2012-09-17 13:41:05 -07:00
|
|
|
return dbus_message_iter_get_signature(&iter->dbus_iterator);
|
|
|
|
}
|
|
|
|
|
|
|
|
EAPI Eina_Bool
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_iter_next(Eldbus_Message_Iter *iter)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_ITERATOR_CHECK_RETVAL(iter, EINA_FALSE);
|
2012-09-17 13:41:05 -07:00
|
|
|
EINA_SAFETY_ON_TRUE_RETURN_VAL(iter->writable, EINA_FALSE);
|
|
|
|
return dbus_message_iter_next(&iter->dbus_iterator);
|
|
|
|
}
|
|
|
|
|
|
|
|
static void
|
|
|
|
get_basic(char type, DBusMessageIter *iter, va_list *vl)
|
|
|
|
{
|
|
|
|
switch (type)
|
|
|
|
{
|
|
|
|
case DBUS_TYPE_BYTE:
|
|
|
|
{
|
|
|
|
uint8_t *byte = va_arg(*vl, uint8_t *);
|
|
|
|
dbus_message_iter_get_basic(iter, byte);
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
case DBUS_TYPE_BOOLEAN:
|
|
|
|
{
|
|
|
|
Eina_Bool *boolean = va_arg(*vl, Eina_Bool *);
|
|
|
|
dbus_bool_t val;
|
|
|
|
dbus_message_iter_get_basic(iter, &val);
|
|
|
|
*boolean = val;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
case DBUS_TYPE_INT16:
|
|
|
|
{
|
|
|
|
int16_t *int16 = va_arg(*vl, int16_t *);
|
|
|
|
dbus_message_iter_get_basic(iter, int16);
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
case DBUS_TYPE_UINT16:
|
|
|
|
{
|
|
|
|
uint16_t *uint16 = va_arg(*vl, uint16_t *);
|
|
|
|
dbus_message_iter_get_basic(iter, uint16);
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
case DBUS_TYPE_INT32:
|
2012-10-09 01:47:59 -07:00
|
|
|
#ifdef DBUS_TYPE_UNIX_FD
|
2012-09-17 13:41:05 -07:00
|
|
|
case DBUS_TYPE_UNIX_FD:
|
2012-10-09 01:47:59 -07:00
|
|
|
#endif
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
|
|
|
int32_t *int32 = va_arg(*vl, int32_t *);
|
|
|
|
dbus_message_iter_get_basic(iter, int32);
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
case DBUS_TYPE_UINT32:
|
|
|
|
{
|
|
|
|
uint32_t *uint32 = va_arg(*vl, uint32_t *);
|
|
|
|
dbus_message_iter_get_basic(iter, uint32);
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
case DBUS_TYPE_INT64:
|
|
|
|
{
|
|
|
|
int64_t *int64 = va_arg(*vl, int64_t *);
|
|
|
|
dbus_message_iter_get_basic(iter, int64);
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
case DBUS_TYPE_UINT64:
|
|
|
|
{
|
|
|
|
uint64_t *uint64 = va_arg(*vl, uint64_t *);
|
|
|
|
dbus_message_iter_get_basic(iter, uint64);
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
case DBUS_TYPE_DOUBLE:
|
|
|
|
{
|
|
|
|
double *double_ieee = va_arg(*vl, double *);
|
|
|
|
dbus_message_iter_get_basic(iter, double_ieee);
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
case DBUS_TYPE_STRING:
|
|
|
|
case DBUS_TYPE_OBJECT_PATH:
|
|
|
|
case DBUS_TYPE_SIGNATURE:
|
|
|
|
{
|
|
|
|
char **string = va_arg(*vl, char**);
|
|
|
|
dbus_message_iter_get_basic(iter, string);
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
default:
|
|
|
|
{
|
|
|
|
ERR("Type not handled %c", type);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
EAPI Eina_Bool
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_iter_fixed_array_get(Eldbus_Message_Iter *iter, int signature, void *value, int *n_elements)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
eldbus: fix _eldbus_message_iter_arguments_vget
Summary:
there is a problem with _eldbus_message_iter_arguments_vget.
Assume: We have a array of type y, there are 3 elements in the array.
Lets say we are iterating with
printf("%c", dbus_message_iter_get_arg_type(iter));
and
dbus_message_iter_next(iter);
throuw the iter.
You will see that this will output yyy. As we are having 3 times v.
While the signature of the message iterator is y.
If you now call eldbus_message_iter_arguments_get(message, "y", &cont)
it will return false, with the errormessage in line 766, reason for this
is that the type of the signature iterator differs from the message
iterator. Because of the upper example.
So all in all: The signature given to the method has not to be equal to
the signature of the message iterator, it has to be equal to the
iterated signature, which cannot be found easily with the eldbus api.
The solution is to only iterate in the message iterator that long until
the signature iterator is at the end, if the type differs in this
region, give a error and return false. Otherwise return true.
The sad thing about this is that it is a behaviour break, but the
behaviour is borked, so its a fix.
I tested this over a week now, without any problem in efl/elm/e.
Reviewers: stefan_schmidt, zmike
Reviewed By: stefan_schmidt
Subscribers: zmike, ceolin, simotek, DaveMDS, cedric
Projects: #efl
Differential Revision: https://phab.enlightenment.org/D3074
2015-10-02 00:13:48 -07:00
|
|
|
int iter_type;
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_ITERATOR_CHECK_RETVAL(iter, EINA_FALSE);
|
2012-09-17 13:41:05 -07:00
|
|
|
EINA_SAFETY_ON_TRUE_RETURN_VAL(iter->writable, EINA_FALSE);
|
eldbus: fix _eldbus_message_iter_arguments_vget
Summary:
there is a problem with _eldbus_message_iter_arguments_vget.
Assume: We have a array of type y, there are 3 elements in the array.
Lets say we are iterating with
printf("%c", dbus_message_iter_get_arg_type(iter));
and
dbus_message_iter_next(iter);
throuw the iter.
You will see that this will output yyy. As we are having 3 times v.
While the signature of the message iterator is y.
If you now call eldbus_message_iter_arguments_get(message, "y", &cont)
it will return false, with the errormessage in line 766, reason for this
is that the type of the signature iterator differs from the message
iterator. Because of the upper example.
So all in all: The signature given to the method has not to be equal to
the signature of the message iterator, it has to be equal to the
iterated signature, which cannot be found easily with the eldbus api.
The solution is to only iterate in the message iterator that long until
the signature iterator is at the end, if the type differs in this
region, give a error and return false. Otherwise return true.
The sad thing about this is that it is a behaviour break, but the
behaviour is borked, so its a fix.
I tested this over a week now, without any problem in efl/elm/e.
Reviewers: stefan_schmidt, zmike
Reviewed By: stefan_schmidt
Subscribers: zmike, ceolin, simotek, DaveMDS, cedric
Projects: #efl
Differential Revision: https://phab.enlightenment.org/D3074
2015-10-02 00:13:48 -07:00
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(n_elements, EINA_FALSE);
|
|
|
|
|
|
|
|
iter_type = dbus_message_iter_get_arg_type(&iter->dbus_iterator);
|
|
|
|
|
|
|
|
if (iter_type == DBUS_TYPE_INVALID)
|
|
|
|
{
|
|
|
|
*n_elements = 0;
|
|
|
|
return EINA_TRUE;
|
|
|
|
}
|
2012-09-17 13:41:05 -07:00
|
|
|
|
|
|
|
EINA_SAFETY_ON_FALSE_RETURN_VAL(
|
2012-12-11 11:50:53 -08:00
|
|
|
(dbus_message_iter_get_arg_type(&iter->dbus_iterator) == signature),
|
2012-09-17 13:41:05 -07:00
|
|
|
EINA_FALSE);
|
|
|
|
dbus_message_iter_get_fixed_array(&iter->dbus_iterator, value, n_elements);
|
|
|
|
return EINA_TRUE;
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* Useful when iterating over arrays
|
|
|
|
*/
|
|
|
|
EAPI Eina_Bool
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_iter_get_and_next(Eldbus_Message_Iter *iter, char signature, ...)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
|
|
|
char type;
|
|
|
|
va_list vl;
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_ITERATOR_CHECK_RETVAL(iter, EINA_FALSE);
|
2012-09-17 13:41:05 -07:00
|
|
|
EINA_SAFETY_ON_TRUE_RETURN_VAL(iter->writable, EINA_FALSE);
|
|
|
|
va_start(vl, signature);
|
|
|
|
|
|
|
|
type = dbus_message_iter_get_arg_type(&iter->dbus_iterator);
|
2014-09-01 03:18:38 -07:00
|
|
|
if (type == DBUS_TYPE_INVALID)
|
|
|
|
{
|
|
|
|
va_end(vl);
|
|
|
|
return EINA_FALSE;
|
|
|
|
}
|
2012-12-11 11:50:11 -08:00
|
|
|
if (type != signature)
|
|
|
|
{
|
|
|
|
if (signature == '(') signature = 'r';
|
|
|
|
else if (signature == '{') signature = 'e';
|
2014-09-04 01:35:05 -07:00
|
|
|
if (type != signature)
|
|
|
|
{
|
|
|
|
va_end(vl);
|
|
|
|
return EINA_FALSE;
|
|
|
|
}
|
2012-12-11 11:50:11 -08:00
|
|
|
}
|
2012-09-17 13:41:05 -07:00
|
|
|
|
|
|
|
if (dbus_type_is_basic(type))
|
|
|
|
get_basic(type, &iter->dbus_iterator, &vl);
|
|
|
|
else
|
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
Eldbus_Message_Iter *sub;
|
|
|
|
Eldbus_Message_Iter **iter_var = va_arg(vl, Eldbus_Message_Iter**);
|
2012-09-17 13:41:05 -07:00
|
|
|
|
|
|
|
sub = _message_iterator_new(EINA_FALSE);
|
2014-08-14 02:52:31 -07:00
|
|
|
if (!sub)
|
|
|
|
{
|
|
|
|
va_end(vl);
|
|
|
|
return EINA_FALSE;
|
|
|
|
}
|
2012-09-17 13:41:05 -07:00
|
|
|
dbus_message_iter_recurse(&iter->dbus_iterator,
|
|
|
|
&sub->dbus_iterator);
|
|
|
|
iter->iterators = eina_inlist_append(iter->iterators,
|
|
|
|
EINA_INLIST_GET(sub));
|
|
|
|
|
|
|
|
*iter_var = sub;
|
|
|
|
}
|
|
|
|
va_end(vl);
|
|
|
|
|
|
|
|
dbus_message_iter_next(&iter->dbus_iterator);
|
|
|
|
return EINA_TRUE;
|
|
|
|
}
|
|
|
|
|
2013-01-02 12:55:57 -08:00
|
|
|
static Eina_Bool
|
2013-04-23 07:40:05 -07:00
|
|
|
_eldbus_message_iter_arguments_vget(Eldbus_Message_Iter *iter, const char *signature, va_list *aq)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2012-12-17 10:24:23 -08:00
|
|
|
int iter_type;
|
|
|
|
DBusSignatureIter sig_iter;
|
2012-09-17 13:41:05 -07:00
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_ITERATOR_CHECK_RETVAL(iter, EINA_FALSE);
|
2012-09-17 13:41:05 -07:00
|
|
|
EINA_SAFETY_ON_TRUE_RETURN_VAL(iter->writable, EINA_FALSE);
|
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(signature, EINA_FALSE);
|
|
|
|
EINA_SAFETY_ON_FALSE_RETURN_VAL(dbus_signature_validate(signature, NULL), EINA_FALSE);
|
|
|
|
|
2012-12-17 10:24:23 -08:00
|
|
|
dbus_signature_iter_init(&sig_iter, signature);
|
|
|
|
iter_type = dbus_message_iter_get_arg_type(&iter->dbus_iterator);
|
edbus: Let arguments_get fail if getting less args than passed
If user passed a string with more elements, return EINA_FALSE on
edbus_message_arguments_get() so he knows not all elements are
initialized. Before this patch, we would notify user of its error if he
did something like:
i) edbus_message_arguments_get(msg, "uu", &a)
ii) edbus_message_arguments_get(msg, "uu", &a, &b)
And "msg" containing only 1 argument.
This also fixes the case in which user is getting the elements of an
array iterator and the array is empty. We were previously returning
EINA_TRUE, even if we were not filling the variable.
Last but not least, if the user was calling
edbus_message_iter_arguments_get() in an empty array, we would return
EINA_FALSE, even if we didn't actually get any element.
SVN revision: 81170
2012-12-17 10:24:31 -08:00
|
|
|
|
2012-12-17 10:24:23 -08:00
|
|
|
while (iter_type != DBUS_TYPE_INVALID)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2012-12-17 10:24:23 -08:00
|
|
|
int sig_type = dbus_signature_iter_get_current_type(&sig_iter);
|
2012-09-17 13:41:05 -07:00
|
|
|
|
eldbus: fix _eldbus_message_iter_arguments_vget
Summary:
there is a problem with _eldbus_message_iter_arguments_vget.
Assume: We have a array of type y, there are 3 elements in the array.
Lets say we are iterating with
printf("%c", dbus_message_iter_get_arg_type(iter));
and
dbus_message_iter_next(iter);
throuw the iter.
You will see that this will output yyy. As we are having 3 times v.
While the signature of the message iterator is y.
If you now call eldbus_message_iter_arguments_get(message, "y", &cont)
it will return false, with the errormessage in line 766, reason for this
is that the type of the signature iterator differs from the message
iterator. Because of the upper example.
So all in all: The signature given to the method has not to be equal to
the signature of the message iterator, it has to be equal to the
iterated signature, which cannot be found easily with the eldbus api.
The solution is to only iterate in the message iterator that long until
the signature iterator is at the end, if the type differs in this
region, give a error and return false. Otherwise return true.
The sad thing about this is that it is a behaviour break, but the
behaviour is borked, so its a fix.
I tested this over a week now, without any problem in efl/elm/e.
Reviewers: stefan_schmidt, zmike
Reviewed By: stefan_schmidt
Subscribers: zmike, ceolin, simotek, DaveMDS, cedric
Projects: #efl
Differential Revision: https://phab.enlightenment.org/D3074
2015-10-02 00:13:48 -07:00
|
|
|
if (sig_type == DBUS_TYPE_INVALID)
|
|
|
|
break;
|
|
|
|
|
2012-12-17 10:24:23 -08:00
|
|
|
if (sig_type != iter_type)
|
2012-10-16 15:35:50 -07:00
|
|
|
{
|
eldbus: fix _eldbus_message_iter_arguments_vget
Summary:
there is a problem with _eldbus_message_iter_arguments_vget.
Assume: We have a array of type y, there are 3 elements in the array.
Lets say we are iterating with
printf("%c", dbus_message_iter_get_arg_type(iter));
and
dbus_message_iter_next(iter);
throuw the iter.
You will see that this will output yyy. As we are having 3 times v.
While the signature of the message iterator is y.
If you now call eldbus_message_iter_arguments_get(message, "y", &cont)
it will return false, with the errormessage in line 766, reason for this
is that the type of the signature iterator differs from the message
iterator. Because of the upper example.
So all in all: The signature given to the method has not to be equal to
the signature of the message iterator, it has to be equal to the
iterated signature, which cannot be found easily with the eldbus api.
The solution is to only iterate in the message iterator that long until
the signature iterator is at the end, if the type differs in this
region, give a error and return false. Otherwise return true.
The sad thing about this is that it is a behaviour break, but the
behaviour is borked, so its a fix.
I tested this over a week now, without any problem in efl/elm/e.
Reviewers: stefan_schmidt, zmike
Reviewed By: stefan_schmidt
Subscribers: zmike, ceolin, simotek, DaveMDS, cedric
Projects: #efl
Differential Revision: https://phab.enlightenment.org/D3074
2015-10-02 00:13:48 -07:00
|
|
|
ERR("Type in iterator different of signature expected:%c got %c", iter_type, sig_type);
|
2012-10-16 15:35:50 -07:00
|
|
|
return EINA_FALSE;
|
|
|
|
}
|
2012-09-17 13:41:05 -07:00
|
|
|
|
2012-12-17 10:24:23 -08:00
|
|
|
if (dbus_type_is_basic(iter_type))
|
2013-01-02 12:55:57 -08:00
|
|
|
get_basic(iter_type, &iter->dbus_iterator, aq);
|
2012-09-17 13:41:05 -07:00
|
|
|
else
|
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
Eldbus_Message_Iter **user_itr = va_arg(*aq, Eldbus_Message_Iter **);
|
|
|
|
Eldbus_Message_Iter *sub_itr;
|
2012-09-17 13:41:05 -07:00
|
|
|
|
|
|
|
sub_itr = _message_iterator_new(EINA_FALSE);
|
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(sub_itr, EINA_FALSE);
|
|
|
|
dbus_message_iter_recurse(&iter->dbus_iterator,
|
|
|
|
&sub_itr->dbus_iterator);
|
|
|
|
iter->iterators = eina_inlist_append(iter->iterators,
|
|
|
|
EINA_INLIST_GET(sub_itr));
|
|
|
|
*user_itr = sub_itr;
|
|
|
|
}
|
2012-12-17 10:24:23 -08:00
|
|
|
|
2012-09-17 13:41:05 -07:00
|
|
|
dbus_message_iter_next(&iter->dbus_iterator);
|
2017-04-26 05:49:37 -07:00
|
|
|
if (!dbus_signature_iter_next(&sig_iter))
|
|
|
|
break;
|
2012-12-17 10:24:23 -08:00
|
|
|
iter_type = dbus_message_iter_get_arg_type(&iter->dbus_iterator);
|
2012-09-17 13:41:05 -07:00
|
|
|
}
|
edbus: Let arguments_get fail if getting less args than passed
If user passed a string with more elements, return EINA_FALSE on
edbus_message_arguments_get() so he knows not all elements are
initialized. Before this patch, we would notify user of its error if he
did something like:
i) edbus_message_arguments_get(msg, "uu", &a)
ii) edbus_message_arguments_get(msg, "uu", &a, &b)
And "msg" containing only 1 argument.
This also fixes the case in which user is getting the elements of an
array iterator and the array is empty. We were previously returning
EINA_TRUE, even if we were not filling the variable.
Last but not least, if the user was calling
edbus_message_iter_arguments_get() in an empty array, we would return
EINA_FALSE, even if we didn't actually get any element.
SVN revision: 81170
2012-12-17 10:24:31 -08:00
|
|
|
|
|
|
|
return dbus_signature_iter_get_current_type(&sig_iter) == DBUS_TYPE_INVALID;
|
2013-01-02 12:55:57 -08:00
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
EAPI Eina_Bool
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_iter_arguments_get(Eldbus_Message_Iter *iter, const char *signature, ...)
|
2013-01-02 12:55:57 -08:00
|
|
|
{
|
|
|
|
va_list ap;
|
|
|
|
Eina_Bool ret;
|
|
|
|
|
|
|
|
va_start(ap, signature);
|
2013-04-23 07:40:05 -07:00
|
|
|
ret = _eldbus_message_iter_arguments_vget(iter, signature, &ap);
|
2013-01-02 12:55:57 -08:00
|
|
|
va_end(ap);
|
|
|
|
|
|
|
|
return ret;
|
|
|
|
}
|
|
|
|
|
|
|
|
EAPI Eina_Bool
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_iter_arguments_vget(Eldbus_Message_Iter *iter, const char *signature, va_list ap)
|
2013-01-02 12:55:57 -08:00
|
|
|
{
|
|
|
|
va_list aq;
|
|
|
|
Eina_Bool ret;
|
|
|
|
|
|
|
|
va_copy(aq, ap);
|
2013-04-23 07:40:05 -07:00
|
|
|
ret = _eldbus_message_iter_arguments_vget(iter, signature, &aq);
|
2013-01-02 12:55:57 -08:00
|
|
|
va_end(aq);
|
|
|
|
|
|
|
|
return ret;
|
2012-09-17 13:41:05 -07:00
|
|
|
}
|
|
|
|
|
|
|
|
EAPI void
|
2013-04-23 07:40:05 -07:00
|
|
|
eldbus_message_iter_del(Eldbus_Message_Iter *iter)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_ITERATOR_CHECK(iter);
|
2012-09-17 13:41:05 -07:00
|
|
|
_message_iterator_free(iter);
|
|
|
|
}
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
EAPI Eldbus_Message *
|
|
|
|
eldbus_message_error_new(const Eldbus_Message *msg, const char *error_name, const char *error_msg)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
Eldbus_Message *reply;
|
2012-09-17 13:41:05 -07:00
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
ELDBUS_MESSAGE_CHECK_RETVAL(msg, NULL);
|
2012-09-17 13:41:05 -07:00
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(error_name, NULL);
|
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(error_msg, NULL);
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
reply = eldbus_message_new(EINA_FALSE);
|
2014-12-10 10:24:54 -08:00
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(reply, NULL);
|
|
|
|
|
2012-09-17 13:41:05 -07:00
|
|
|
reply->dbus_msg = dbus_message_new_error(msg->dbus_msg,
|
|
|
|
error_name, error_msg);
|
|
|
|
|
2013-06-22 04:15:44 -07:00
|
|
|
dbus_message_iter_init(reply->dbus_msg, &reply->iterator->dbus_iterator);
|
2012-09-17 13:41:05 -07:00
|
|
|
|
|
|
|
return reply;
|
|
|
|
}
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
EAPI Eldbus_Message *
|
|
|
|
eldbus_message_method_return_new(const Eldbus_Message *msg)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
Eldbus_Message *reply;
|
|
|
|
ELDBUS_MESSAGE_CHECK_RETVAL(msg, NULL);
|
2012-09-17 13:41:05 -07:00
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
reply = eldbus_message_new(EINA_TRUE);
|
2016-09-19 19:18:52 -07:00
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(reply, NULL);
|
|
|
|
|
2012-09-17 13:41:05 -07:00
|
|
|
reply->dbus_msg = dbus_message_new_method_return(msg->dbus_msg);
|
|
|
|
|
|
|
|
dbus_message_iter_init_append(reply->dbus_msg,
|
|
|
|
&reply->iterator->dbus_iterator);
|
|
|
|
|
|
|
|
return reply;
|
|
|
|
}
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
EAPI Eldbus_Message *
|
|
|
|
eldbus_message_signal_new(const char *path, const char *interface, const char *name)
|
2012-09-17 13:41:05 -07:00
|
|
|
{
|
2013-04-23 07:40:05 -07:00
|
|
|
Eldbus_Message *msg;
|
2012-09-17 13:41:05 -07:00
|
|
|
|
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(path, NULL);
|
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(interface, NULL);
|
|
|
|
EINA_SAFETY_ON_FALSE_RETURN_VAL(name, NULL);
|
|
|
|
|
2013-04-23 07:40:05 -07:00
|
|
|
msg = eldbus_message_new(EINA_TRUE);
|
2012-09-17 13:41:05 -07:00
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(msg, NULL);
|
|
|
|
|
|
|
|
msg->dbus_msg = dbus_message_new_signal(path, interface, name);
|
|
|
|
dbus_message_iter_init_append(msg->dbus_msg,
|
|
|
|
&msg->iterator->dbus_iterator);
|
|
|
|
|
|
|
|
return msg;
|
|
|
|
}
|