问题
Can anyone help with writing a semaphore function in fortran? I have multiple processes running and I have to synchronize them using semaphore. Such a code could be found for C++ etc., but I could not find any such code for fortran.
If I could call C/C++ function from fortran code, that would also suffice, since C++ semaphore function is already there.
PS: (Additional Explanation) Here is the code which works for C++. I have some fortran applications (as part of standard benchmark) but no semaphore code to synchronize them.
int get_semaphore ()
{
int sem_id;
sem_id = semget(SEM_ID, 1, IPC_CREAT | 0666);
if (sem_id == -1) {
perror("get_semaphore: semget");
exit(1);
}
return sem_id;
}
int set_semaphore (int sem_id, int val)
{
return semctl(sem_id, 0, SETVAL, val);
}
void decrement_semaphore (int sem_id)
{
struct sembuf sem_op;
sem_op.sem_num = 0;
sem_op.sem_op = -1;
sem_op.sem_flg = 0;
semop(sem_id, &sem_op, 1);
}
void wait_semaphore (int sem_id)
{
struct sembuf sem_op;
sem_op.sem_num = 0;
sem_op.sem_op = 0;
sem_op.sem_flg = 0;
semop(sem_id, &sem_op, 1);
}
Thanks for the help in advance.
回答1:
OpenMP provides semaphores under the term "lock". Normally these aren't used since OpenMP provides higher level tasking constructs, but if you want to do it yourself, that could be a way to do explicit locking/unlocking with Fortran.
P.S. If you want to do it from Fortran by calling the C code that you already have, that could by done by using the ISO C Binding of Fortran 2003. There are many questions/answers here about how this works. I drafted declarations for your Fortran program to match the C routines. These tell the Fortran compiler how to call the C routines using the calling conventions of the C compiler. These are untested and may need debugging:
use iso_c_binding
interface semaphore_stuff
function get_semaphore () bind (C, name="get_sempaphore")
import
integer (c_int) :: get_semaphore
end function get_semaphore ()
function set_semaphore (sem_id, int val) bind (C, name="get_sempaphore")
import
integer (c_int) :: set_semaphore
integer (c_int), intent (in), value :: sem_id
integer (c_int), intent (in) value :: val
end function set_semaphore
subroutine decrement_semaphore (sem_id) bind (C, name="decrement_semaphore")
import
integer (c_int), intent (in), value :: sem_id
end subroutine decrement_semaphore
subroutine wait_semaphore (sem_id) bind (C, name="wait_semaphore")
import
integer (c_int), intent (in), value :: sem_id
end subroutine wait_semaphore
end interface semaphore_stuff
来源:https://stackoverflow.com/questions/8564785/semaphores-for-fortran