0

I declare a global variable and initialize it with 0. In main () function i create two threads. The first thread function increments the global variable upto the received arguments (function parameter) using a for loop, while the second function decrements the global variable same times using for loop. When i pass 1000 as arguments the program works fine but when i pass 100000 the global variable value should be zero at the end but i found the value is not zero. I also called the join function for both threads but doesn't works.

    #include "stdio.h"
    #include "stdlib.h"
    #include "pthread.h"
    int globVar =0;


    void *incFunct(void* val){
      for (int i=0; i<val; i++)
        globVar++;
      pthread_exit(NULL); 
      }

    void *decFunct(void* val){
     for (int i=0; i<val; i++)
       globVar--;
     pthread_exit(NULL);
      }

    int main()
     {

       pthread_t tid[2];
       int val = 1000000;
       printf("Initial value of Global variable : %d \n", globVar);
       pthread_create(&tid[0], NULL, &incFunct, (void*)val);

       pthread_create(&tid[1], NULL, &decFunct, (void*)val);

       pthread_join(tid[0], NULL);
       pthread_join(tid[1], NULL);

       printf("Final Value of Global Var : %d \n", globVar);
        return 0;
         }
4
  • 1
    Show us your source code Commented Mar 20, 2020 at 8:45
  • Saif please post your source here, I am guessing there maybe some logical bug in your code. Review your code as well and make sure you understand how to use a join. Commented Mar 20, 2020 at 9:04
  • user734028 here is the code. Commented Mar 20, 2020 at 13:28
  • I am surprised i<val compiles, it compares an int with void*. Always compile with -Wall -Wextra -Werror. Use atomic_int instead of int for globVar. Commented Mar 20, 2020 at 15:35

2 Answers 2

1

Yeah, you can't do that. Reasonably, you could end up with globVar having any value between -10000000 and +1000000; unreasonably, you might have invited the compiler to burn down your home (ask google about undefined behaviour).

You need to synchronize the operations of the two threads. One such synchronization is with a pthread_mutex_t; and you would acquire the lock (pthread_mutex_lock()) before operating on globVar, and release the lock (pthread_mutex_unlock()) after updating globVar.

For this particularly silly case, atomics might be more appropriate if your compiler happens to support them (/usr/include/stdatomic.h).

Sign up to request clarification or add additional context in comments.

Comments

1

One thing that might happen is that the inc thread and the dec thread don't see consistent values for globVar. If you increment a variable you think has a value of 592, and, at the same time, I decrement what I think is the same variable but with a value of 311 — who wins? What happens when it's all over?

Without memory synchronization, you can't predict what will happen when multiple threads update the same memory location. You might have problems with cache coherency, variable tearing, and even reordered operations. Mutexes or C11 atomic variables are two ways to avoid these problems.

(As an aside, I suspect you don't see this problem with one thousand iterations because the first thread finishes well before the second even looks at globVar, and your implementation happens to update memory for that latter thread's consistency.)

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.