Share via


A.25 Examples of the copyprivate Data Attribute Clause

 

The new home for Visual Studio documentation is Visual Studio 2017 Documentation on docs.microsoft.com.

Example 1: The copyprivate clause (Section 2.7.2.8 on page 32) can be used to broadcast values acquired by a single thread directly to all instances of the private variables in the other threads.

float x, y;  
#pragma omp threadprivate(x, y)  
  
void init( )   
{  
    float a;  
    float b;  
  
    #pragma omp single copyprivate(a,b,x,y)  
    {  
        get_values(a,b,x,y);  
    }  
  
    use_values(a, b, x, y);  
}  

If routine init is called from a serial region, its behavior is not affected by the presence of the directives. After the call to the get_values routine has been executed by one thread, no thread leaves the construct until the private objects designated by a, b, x, and y in all threads have become defined with the values read.

Example 2: In contrast to the previous example, suppose the read must be performed by a particular thread, say the master thread. In this case, the copyprivate clause cannot be used to do the broadcast directly, but it can be used to provide access to a temporary shared object.

float read_next( )   
{  
    float * tmp;  
    float return_val;  
  
    #pragma omp single copyprivate(tmp)  
    {  
        tmp = (float *) malloc(sizeof(float));  
    }  
  
    #pragma omp master  
    {  
        get_float( tmp );  
    }  
  
    #pragma omp barrier  
    return_val = *tmp;  
    #pragma omp barrier  
  
    #pragma omp single  
    {  
       free(tmp);  
    }  
  
    return return_val;  
}  

Example 3: Suppose that the number of lock objects required within a parallel region cannot easily be determined prior to entering it. The copyprivate clause can be used to provide access to shared lock objects that are allocated within that parallel region.

#include <omp.h>  
  
omp_lock_t *new_lock()  
{  
    omp_lock_t *lock_ptr;  
  
    #pragma omp single copyprivate(lock_ptr)  
    {  
        lock_ptr = (omp_lock_t *) malloc(sizeof(omp_lock_t));  
        omp_init_lock( lock_ptr );  
    }  
  
    return lock_ptr;  
}