Search code examples
bashshellshrace-condition

shell: race condition in assigning global variable


I am working on a script that goes:

#script_1.sh
function a() {
    export var1='...some calculations on $@...';
}

function b() {
    a "$@"
    local loc_b=$var1
}

function c() {
    a "$@"
    local loc_c=$var1
}

#script_2.sh
source script_1.sh
b val1 &
c val2 &
b val2 &

function a has getopt command and parses parameters for b and c. This has been simplified to a great extent.

When I call function b, function c and function b again at the end as background processes, I worry that I might have a race condition on assigning the exported var1 variable to the local variable.

  1. If I can guarantee that calls to function b or function c will be as background processes, do I have to worry about the race condition here?

  2. If there is no race, can I get away by not declaring the local variables for each function?


Solution

  • Each background process gets its own copy of the environment. Child process can't change the environment of its parent process. So, there's no race condition: if you change a global variable before running a background process, the process will get the new value copied. If you run a background process before changing the value, the process will see the old value.

    #!/bin/bash
    
    global=1
    
    inc () {
        ((++global))
        echo inc: $global
    }
    
    dec () {
        ((--global))
        echo dec: $global
    }
    
    inc & dec &
    # 2   0
    
    global=10
    inc & dec & inc & dec &
    # 11  9     11    9