2012-04-17 19 views
0

スレッドセーフである4バイトトランザクション/セッションIDを提供できるので、以下のコードを共有してくれてありがとうございます。 16スレッド/ 16プロセスに対して非常にまともな量の一意のIDを提供します。 以下は関数の基本テストです.p_noはプロセス番号です。スレッドセーフ固有のトランザクションID

int get_id(int choice, unsigned int pid); 
    int start_(int id); 
    void *print_message_function(void *ptr); 
    void *print_message_function2(void *ptr); 

     unsigned int pid_arr[15][2]; 
    int p_no = 1; 
    int main() 
    { 
     pthread_t thread1, thread2; 
     char *message1 = "Thread 1"; 
     char *message2 = "Thread 2";  
     int iret1, iret2; 
    int s,f; 
     for (s=0;s<15;s++) 
     { 
     for (f=0;f<2;f++) 
     pid_arr[s][f]= 0; 

     } 

     iret1 = pthread_create(&thread1, NULL, print_message_function, (void*) message1); 
     iret2 = pthread_create(&thread2, NULL, print_message_function2, (void*) message2); 

     pthread_join(thread1, NULL); 
     pthread_join(thread2, NULL); 
     exit(0); 
    } 

    void *print_message_function(void *ptr) 
    { 
    int one=0; 

    get_id(1/*register*/,(unsigned int)pthread_self()); 
    while (1) 
    { 

    int ret = get_id(0,(unsigned int)pthread_self()); 
    printf("thread 1 = %u\n",ret); 
    sleep(1); 
    } 

    } 
    void *print_message_function2(void *ptr) 
    { 
    int one=0; 

    get_id(1/*register*/,(unsigned int)pthread_self()); 

    while (1) 
    { 

    int ret = get_id(0,(unsigned int)pthread_self()); 
    printf("thread 2 = %u\n",ret); 
    sleep(1); 
    } 

    } 


    int get_id(int choice, unsigned int pid) 
    { 
    int x; 


     if (choice==1) // thread registeration part 
     { 
      for(x=0;x<15;x++) 
     { 
      if (pid_arr[x][0] == 0) 
      { 
      pid_arr[x][0] = pid;  
      pid_arr[x][1] = ((p_no<<4) | x) << 24; 

      break; 
      } 
     } 

     } 

    int y; 
      for(y=0;y<15;y++) // tranaction ID part 
     { 
      if (pid_arr[y][0]==pid) 
      { 

      if(pid_arr[y][1] >= ((((p_no<<4) | y) << 24) | 0xfffffd)) 
      ((p_no<<4) | x) << 24; 
      else 
      pid_arr[y][1]++; 
      return (unsigned int) pid_arr[y][1]; 
      break; 
      } 
     } 

    } 
+0

申し訳ありませんが、あなたの質問は何ですか? –

+0

これは実際には問題ではありません。マルチスレッドセッション指向のアプリケーションに固有のセッションIDを提供するには、これまでに達成したことを共有しています。 –

+0

おそらくhttp://codereview.stackexchange.com/に投稿する方が良いでしょう。 – weston

答えて

1

スレッドセーフではありません。例えば、登録部に、次の行が最終的に問題となるであろう:

1:  if (pid_arr[x][0] == 0) 
     { 
2:  pid_arr[x][0] = pid;  

スレッド1は、ライン1を実行し、それがライン2を実行する前に、コンテキストスイッチが発生した場合、スレッド2が実行できるとの線1を実行しますその点では、両方のスレッドがpid_arr配列内の同じ位置を「所有」することになります。または、2番目の行を実行する最後の行はその位置を所有し、もう1つは配列内の位置を所有しません。

+0

@BagDev:いいえ、それは修正されません。最良のことは、同期コンストラクト(mutex、semaphoreなど)を使用して競合条件がないことを確認することです。ロックフリーのマルチスレッドは非常に困難です。 –

+0

そうです、登録部分で睡眠をとると安全でしょうか?または登録部分にのみmutexを使用しますか? –

+0

@BagDev:徹底的な検査では、スレッドセーフであると信じています...睡眠は必ずしも十分ではありませんが、最初のスレッド(イベントまたはミューテックスの方が良いでしょう)登録を完了しました。それ自体でスリープしても、スレッドが実際に終了したことを保証するものではありません。 –

0

ファイルスコープまたは外部変数を読み書きするコードをシリアル化する必要があるか、スレッドセーフではないコード。

提供されたサンプルはスレッドセーフではありません。

関連する問題