-1

thrift を使用して c (c_glib) でクライアント/サーバー プログラムを実装しようとしています。

関数の引数として変数を渡すクライアント/サーバーを実装しました。ここで、構造体を関数の引数として渡す必要があります。

使用しているthriftファイルを以下に示します

#!/usr/local/bin/thrift --gen c_glib


struct packet {
        1: i32 header,
        2: i32 data
}

service Calculator {
        void ping(),
        i32 calculate(1:i32 id, 2:i32 num),
        void stop_transfer(),
        void set_packet(1:packet pac_data)

}

構造を渡すために私が従った手順は次のとおりです。

  • クライアント側
    1. g_object_new(TYPE_PACKET, NULL)
    2. 構造体のポインタをサーバーに渡します。calculator_if_set_packet (client, trans_packet, &error)
    3. g_object_get(tans_packet, "header", &head, "data", &dat, NULL) でサーバーのデータセットを取得
    4. サーバーのデータセットが反映されていることを示す構造体を出力クライアントに戻る

クライアント側の関連コードを以下に示します

int main (void) 
{
    gint head;
    gint dat;

    packet *trans_packet;

    trans_packet = g_object_new (TYPE_PACKET, NULL);

    if(!error && calculator_if_set_packet (client, trans_packet, &error)) {
        g_object_get((packet *) trans_packet,
             "header", &head,
             "data", &dat,
             NULL);

        printf("struct->header : %d\n", head);
        printf("struct->data : %d\n", dat);
    }

    g_object_unref (trans_packet);

}
  • サーバー側
    1. g_object_get(pac_data, "header", &header, "data", &data, NULL) で pac_data のプロパティを取得
    2. g_object_setg_object_get(tans_packet, "header", 111, "data", 999, NULL)

サーバー側の機能を以下に示します

static gboolean 
tutorial_calculator_handler_set_packet(CalculatorIf *iface,
                                  const packet * pac_data,
                                  GError **error)
{
    gint header;
    gint data;

    THRIFT_UNSED_VAR (iface);
    THRIFT_UNUSED_VAR (error);

    g_object_get((packet *) pac_data,
             "header", &header,
             "data", &data,
             NULL);

    g_object_set((packet *) pac_data,
             "header", 123,
             "data", 999,
             NULL);

    return TRUE;
}

これを行っているとき、calculator_if_set_packet() を呼び出しているときに、サーバーはクライアントに何も返していません。

誰でもこれについて私を助けることができますか?

4

2 に答える 2

0

あなたが示した構造体は、ビットフィールドであってもC構文を使用していません:

struct packet {  //Not C syntax
        1: i32 header, //1nvalid struct field declaration
        2: i32 data    //invalid struct field declaration
}                      //missing ;  

構造体を引数として取る関数のプロトタイプを表示していませんが、たとえば、構造体が次のように定義されているとします。

typedef struct {
    int header;
    int data;
} PACKET;  //symbol PACKET would be used like your "struct packet"

次に、この typedef を使用して、次のようにインスタンスとその構造体へのポインターを作成できます。

PACKET パケット、*pPacket;

main では、次のようにインスタンスを使用してポインターを初期化できます。

int main(void)
{
    //pointer   instance
      pPacket = &packet;
      pPacket = malloc(sizeof(PACKET));//provide memory for pointer
      ...

      free(pPacket);//free dynamic memory 
      return 0;
}

次に、たとえば、インスタンスを取る 1 つの関数プロトタイプと、その構造体へのポインターを取る別の関数プロトタイプがあるとします。

void someFunc1(PACKET pkt);  // takes an instance of PACKET
void someFunc2(PACKET *pkt);  //takes an instance of PACKET *

次に、メインで、次のように渡すことができます。

int main(void)
{
    pPacket = &packet;  //initialize pointer using instance
    pPacket = malloc(sizeof(PACKET));//provide memory for pointer

    someFunc1(packet);  //pass instance of PACKET
    someFunc2(pPacket); //pass pointer to PACKET
    someFunc2(&packet); //same as previous
    ...
    free(pPacket);//free dynamic memory 
    return 0;
}
于 2015-04-13T13:58:02.407 に答える