Entendiendo escrituras concurrentes de archivos de múltiples procesos

De aquí :Es el archivo adjunto atómico en UNIX

Considere un caso en el que múltiples procesos abren el mismo archivo y lo agreguen. O_APPEND garantiza que la búsqueda hasta el final del archivo y luego el inicio de la operación de escritura es atómica. Por lo tanto, varios procesos pueden adjuntarse al mismo archivo y ningún proceso sobrescribirá la escritura de ningún otro proceso en la medida en que cada tamaño de escritura sea <= PIPE_BUF.

Escribí un programa de prueba donde varios procesos se abren y escriben en el mismo archivo (write(2)). Me aseguro de que cada tamaño de escritura sea> PIPE_BUF (4k). Esperaba ver casos en los que un proceso sobrescribe los datos de otra persona. Pero eso no sucede. He probado con diferentes tamaños de escritura. ¿Es solo suerte o hay una razón por la que eso no sucede? Mi objetivo final es entender si los múltiples procesos que se agregan al mismo archivo deben coordinar sus escrituras.

Aquí está el programa completo. Cada proceso crea un búfer int, llena todos los valores con surank, abre un archivo y le escribe.

Especificaciones: OpenMPI 1.4.3 en Opensuse 11.3 de 64 bits

Compilado como: mpicc -O3 test.c, ejecutado como: mpirun -np 8 ./a.out

#include <stdio.h>
#include <stdlib.h>
#include <mpi.h>
#include <fcntl.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>

int 
main(int argc, char** argv) {
    int rank, size, i, bufsize = 134217728, fd, status = 0, bytes_written, tmp_bytes_written;
    int* buf;
    char* filename = "/tmp/testfile.out";

    MPI_Init(&argc, &argv);
    MPI_Comm_rank(MPI_COMM_WORLD, &rank);
    MPI_Comm_size(MPI_COMM_WORLD, &size);

    buf = (int*) malloc (bufsize * sizeof(int));   
    if(buf == NULL) {
        status = -1;
        perror("Could not malloc");
        goto finalize;
    }
    for(i=0; i<bufsize; i++) 
        buf[i] = rank;

    if(-1 == (fd = open(filename, O_APPEND|O_WRONLY, S_IWUSR))) {
        perror("Cant open file");
        status = -1;
        goto end;
        exit(-1);
    }

    bytes_written = 0;
    if(bufsize != (tmp_bytes_written = write(fd, buf, bufsize))) {
        perror("Error during write");
        printf("ret value: %d\n", tmp_bytes_written);
        status = -1;
        goto close;
    }

close:
    if(-1 == close(fd)) {
        perror("Error during close");
        status = -1;
    }
end:
    free(buf);
finalize:
    MPI_Finalize();
    return status;
}

Respuestas a la pregunta(3)

Su respuesta a la pregunta