| <html>
|
| <head>
|
| <title>shmem_int_add</title>
|
| </head>
|
| <h2 id="top">shmem_int_add</h2>
|
| <h4>Purpose</h4>
|
|
|
|
|
| <p>Performs an atomic add operation on a symmetric data object.
|
| </p>
|
|
|
| <h4>C syntax</h4>
|
|
|
| <pre>
|
| #include <shmem.h>
|
|
|
| void shmem_int_add(int *target, int value, int pe);
|
|
|
| </pre>
|
|
|
| <h4>Parameters</h4>
|
|
|
|
|
| <dl>
|
| <dt class="bold">INPUT</dt>
|
| <dd>
|
|
|
| </dd>
|
| <dt class="bold ">target</dt>
|
| <dd>The remotely accessible integer data object to be updated on the PE.
|
| </dd>
|
| <dt class="bold ">value</dt>
|
| <dd>Value to be atomically written to the target PE. Value is the same type as target.
|
| <dt class="bold ">pe</dt>
|
| <dd>An integer indicating the PE number on which target is to be
|
| updated.
|
| </dd>
|
| </dl>
|
|
|
| <h4>Description</h4>
|
|
|
| <div class="ledi">
|
| <p>The shmem_int_add routine performs an atomic add operation. </p>
|
| <p>It adds value to the variable pointed by target on the processing element specified by pe.</p>
|
| <p>The atomic accessing of the shared variable is guaranteed only when that variable is updated solely using IBM openshmem functions.</p>
|
|
|
| <h4>IBM NOTES</h4>
|
| <div class="ledi">
|
| <dl>
|
| <p>To utilize the hardware atomic operations support of the PERCS system, the variables of these operations should be aligned with their natural byte alignments. For example, an int variable should be 4-byte aligned; a long long variable should be 8-byte aligned. If the participating variables are not aligned, the operation is done in software with sub-optimal performance</p>
|
| </dd>
|
| </dl>
|
| <h4>C examples</h4>
|
| <pre>
|
| #include <stdlib.h>
|
| #include <stdio.h>
|
|
|
| #include <shmem.h>
|
|
|
| static int gIntValue_cswap;
|
| static int gIntValue_add;
|
| static int gIntValue_fadd;
|
|
|
| static long gLock;
|
|
|
| int main (int argc, char* argv[])
|
| {
|
| int total_tasks = -1;
|
| int my_task = -1;
|
|
|
| start_pes(0);
|
|
|
| total_tasks = _num_pes();
|
|
|
| if (total_tasks <= 0) {
|
| printf("FAILED\n");
|
| exit(1);
|
| } else {
|
| printf("number of pes is %d\n", total_tasks);
|
| }
|
|
|
| if (total_tasks < 2 || total_tasks % 2) {
|
| printf("FAILED: The number of pes should be an even number. (at least 2)\n");
|
| exit(1);
|
| }
|
|
|
| my_task = _my_pe();
|
|
|
| if (my_task < 0){
|
| printf("FAILED\n");
|
| exit(1);
|
| } else {
|
| printf("my pe id is %d\n", my_task);
|
| }
|
|
|
| gIntValue_cswap = -1;
|
| shmem_barrier_all();
|
|
|
| printf("remote cswap operations ...\n");
|
|
|
| if (my_task != 0) {
|
| int oldval = shmem_int_cswap(&gIntValue_cswap, -1, my_task, 0);
|
| if (oldval == -1) {
|
| printf("pe %d was the winner\n", my_task);
|
| } else {
|
| printf("pe %d was a loser\n", my_task);
|
| }
|
| }
|
|
|
| gIntValue_add = 0;
|
| shmem_barrier_all();
|
|
|
| printf("remote add operations ...\n");
|
| shmem_int_add(&gIntValue_add, 1, 0);
|
|
|
| gIntValue_fadd = 0;
|
| shmem_barrier_all();
|
| if (my_task == 0) {
|
| printf("initial value was 0, current value is %d after %d remote add operations\n",
|
| gIntValue_add, total_tasks);
|
| }
|
|
|
| printf("remote fadd operations ...\n");
|
| int oldVal = shmem_int_fadd(&gIntValue_fadd, 1, 0);
|
| printf("old value before remote fadd is %d\n", oldVal);
|
|
|
| shmem_barrier_all();
|
|
|
| printf("remote lock operations ...\n");
|
| shmem_set_lock(&gLock);
|
| printf("pe %d got the lock\n", my_task);
|
| shmem_clear_lock(&gLock);
|
|
|
| shmem_barrier_all();
|
|
|
| printf("PASSED\n");
|
| return 0;
|
| }
|
| </pre>
|
|
|
| <h4>Related information</h4>
|
|
|
| <p>Subroutines: shmem_fadd
|
| </p>
|
| <hr><a href="apiIndex.html">OpenSHMEM API Index</a> |
| </html> |