2011年3月29日 星期二

如何用dbus傳送array of struct

大部份dbus在傳送的資料型態,都是G_TYPE_INT、G_TYPE_STRING等簡單型態,


但如果要傳的資料型態,是一個struct的陣列 (array of struct)呢?


GTYPE並沒有適合的型態可以用,所以要做一些轉換,其中一個方法就是把array of struct轉成array of array of byte


聽起來像饒口令,但其實就是把struct轉成array of byte而已。


 


首先,xml檔要定義這個array of array of byte


<?xml version="1.0" encoding="UTF-8" ?>
<node name="/">
  <interface name="myInterface">
    <method name="myMethod">
        <arg name="myData" type="aay" />
    </method>
  </interface>
</node>


在這裡指定myData的型態為aay,就是array of (array of byte)。


 


接著,client端要送的話,要先定義好你要的struct:


typedef struct{
        gchar *title;
        gint price;
}BookInfo;


然後建立一個GPtrArray,用來裝許多個BookInfo,


GPtrArray *book_array = g_ptr_array_new();


BookInfo *book1 = (BookInfo *)g_new0(BookInfo, 1);     //建立第一本書的資訊
book1->title = g_strdup("Harry Poter");
book1->price = 199;
g_ptr_array_add(book_array, book1);   //把第一本書裝進book_array

BookInfo *book2 = (BookInfo *)g_new0(BookInfo, 1);    //建立第二本書的資訊
book2->title = g_strdup("The Da Vinci Code");
book2->price = 299;
g_ptr_array_add(book_array, book2);   //把第二本書裝進book_array


在這裡就是用g_ptr_array_add來把BookInfo裝進book_array。


 


最後要送出dbus:


dbus_g_proxy_call (proxy, "myMethod", &error,
  dbus_g_type_get_collection("GPtrArray", DBUS_TYPE_G_UCHAR_ARRAY), book_array,
G_TYPE_INVALID,
G_TYPE_INVALID)


這邊需要用dbus_g_type_get_collection的函式來指定book_array的型態。


 


而在server端,收到array of array of byte,也就是GPtrArray之後,要把它還原成原來的資料:


// server端也要知道BookInfo的struct是什麼


typedef struct{
        gchar *title;
        gint price;
}BookInfo;


 


// server端接收的function


gboolean test_obj_my_method (TestObj *obj, GPtrArray *array, GError **error)
{

        for(i=0;i<array->len;i++){
                BookInfo *book = (BookInfo *)g_new0(Booknfo, 1);
                book = (BookInfo *)g_ptr_array_index(array, i);
                printf("title=%s, price=%d\n", book->title, book->price);
        }

        return TRUE;
}


接收端一樣要用GPtrArray來接,接到之後先建立BookInfo,然後用g_ptr_array_index的函式,來把第i個元素拿出來,存入BookInfo裡面。


沒有留言:

張貼留言