it-swarm.com.de

Warum erstellt open () meine Datei mit den falschen Berechtigungen?

Ich versuche, etwas Text aus einer Datei zu lesen und ihn mit open(), read() und write() in eine andere zu schreiben.

Dies ist meine open() für die zu schreibende Datei (ich möchte eine neue Datei erstellen und in sie schreiben):

fOut = open ("test-1", O_RDWR | O_CREAT | O_SYNC);

Das setzt Dateiberechtigungen auf etwas, das ich überhaupt nicht verstehe. Dies ist die Ausgabe von ls -l:

---------T 1 chaitanya chaitanya 0 2010-02-11 09:38 test-1

Sogar die Leseberechtigung ist gesperrt. Ich habe versucht, danach zu suchen, konnte aber ALLES nicht finden .. Merkwürdigerweise schreibt write() immer noch erfolgreich Daten in die Datei.

Wenn ich einen 'chmod 777 test-1' mache, funktionieren die Dinge wieder einwandfrei.

Könnte mir bitte jemand mitteilen, wo ich bei meinem offenen Anruf falsch liege?

Vielen Dank!

Als Referenz habe ich unten das vollständige Programm eingefügt:

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <fcntl.h>

int main () {

    char buffer[512], ch;

    int fIn, fOut, i;
    ssize_t bytes;
    FILE *fp = NULL;

    //open a file
    fIn = open ("test", O_RDONLY);
    if (fIn == -1) {
        printf("\nfailed to open file.");
        return 1;
    }

    //read from file
    bytes =  read (fIn, buffer, sizeof(buffer));
    //and close it
    close (fIn);

    printf("\nSuccessfully read %d bytes.\n", bytes);

    //Create a new file
    fOut = open ("test-1", O_RDWR | O_CREAT | O_SYNC);

    printf("\nThese are the permissions for test-1\n");
    fflush(stdout);
    system("ls -l test-1");

    //write to it and close it.
    write (fOut, buffer, bytes);
    close (fOut);


    //write is somehow locking even the read permission to the file. Change it.
    system("chmod 777 test-1");

    fp = fopen ("test-1", "r");
    if (fp == NULL) {
        printf("\nCan't open test-1");
        return 1;
    }

    while (1)
    {
        ch = fgetc(fp);
        if (ch == EOF)
            break;
        printf("\n%c", ch);
    }

    fclose (fp);

    return 0;
}
44
Chaitanya

open () verwendet ein drittes Argument, nämlich die Gruppe von Berechtigungen, d. h.

open(filename, O_RDWR|O_CREAT, 0666)

0666 ist eine Oktalzahl, d. H., Jede der 6 entspricht drei Erlaubnisbits

6 = rw

7 = rwx

Es ist eine typische Falle. Der Compiler ermöglicht es Ihnen, das Berechtigungsargument wegzulassen, da beim Öffnen einer vorhandenen Datei die Berechtigungsbits nicht sinnvoll sind. Wenn Sie das Argument jedoch vergessen, wenn Sie eine Datei erstellen, erhalten Sie einen zufälligen Satz von Berechtigungen, z. 0000 in Ihrem Fall (---).

74
Antti Huima

Beim Lesen von http://linux.die.net/man/2/open scheint es, als hätten Sie den mode-Parameter für das Öffnen verloren:

der Modus muss angegeben werden, wenn sich O_CREAT in den Flags befindet. Andernfalls wird er ignoriert. Der Argumentmodus gibt die Berechtigungen an, die verwendet werden sollen, wenn eine neue Datei erstellt wird.

9
ZeissS

Diese Frage hat mir in letzter Zeit geholfen, deshalb wollte ich meinen Teil dazu beitragen, etwas mehr Tiefe in das Geschehen einzufügen. Wie bereits gesagt, haben Sie das dritte Argument von open() verpasst. Die angezeigten Berechtigungen sind jedoch nicht zufällig. Sie kommen vom Stapel. Sehen Sie sich das folgende Code-Snippet an:

    asm("Push $0");
    asm("Push $0");
    asm("Push $0");
    fd = open("base", O_RDWR|O_CREAT);

Beachten Sie folgendes Ergebnis:

    ----------. 1 user user 4 Feb 26 08:21 base

Ändern wir den ersten Push auf 1, d. H. Die Berechtigung zum Ausführen:

    asm("Push $1;Push $0;Push $0");
    fd = open("base", O_RDWR|O_CREAT);

und wir bekommen:

    ---------x. 1 user user 4 Feb 26 08:25 base

Ändern Sie den Push auf 4, d. H. Leseberechtigung, und machen Sie sich mit den beiden anderen Werten beschäftigt:

    asm("Push $4;Push $5;Push $6");
    fd = open("base", O_RDWR|O_CREAT);

und wir bekommen:

    -------r--. 1 user user 4 Feb 26 08:27 base

So können wir sehen, dass der dritte Wert, der aus dem Stapel gesprungen ist (zuerst gedrückt), das ist, was wirklich zählt. Zum Spaß können wir schließlich 5 und dann 50 versuchen, was jeweils zu folgendem Ergebnis führt:

    -------r-x. 1 user user 4 Feb 26 08:27 base
    ----rw----. 1 user user 4 Feb 26 08:28 base

Hoffe, das bringt Klarheit!

8
Billy

Tatsächlich filtert umask() nur Berechtigungen und legt sie nicht fest. Der typische umask()-Wert ist 0002 ("Schreibe die Erlaubnis nicht an die Welt weitergeben"). Wenn Ihr Moduswert in open( "file", O_CREAT, 0777) alle Berechtigungen erteilt hat, hätte die resultierende Datei 775 als Berechtigungen. 

3
rgt

Für die Frage nicht unbedingt relevant, aber die akzeptierte Antwort könnte diesen klarstellenden Punkt verwenden:

Es gibt eine Beziehung zwischen rwx und seiner numerischen Darstellung, die man sehen kann, wenn man das Vorhandensein eines Buchstabens als eine binäre 1 und sein Fehlen als eine binäre 0 behandelt. 

z.B.

rwx  <-->  111 (binary) <-->  7 (octal)

r--  <-->  100 (binary) <-->  4 (octal)

-wx  <-->  011 (binary) <-->  3 (octal) 

Als weiteren Nachtrag können Sie jetzt den Befehl chmod betrachten:

chmod 777 filename.extension -> rwxrwxrwx-Berechtigungen

777 <--> 111 111 111 <--> rwx rwx rwx

oder: chmod 654 Dateiname.Erweiterung -> rw-r-x-r--

654 <--> 110 101 100 <--> rw- r-x r--

Hoffe das ist informativ!

1
Evan

sie können den umask(0);-Systemaufruf aufrufen, bevor Sie den open();-Systemaufruf verwenden, um die Auswahlberechtigungen für die Datei richtig festzulegen.

0
Abdo

Dies ist eine Art alter Thread, aber ich denke, die Leute sollten sich der Bibliothek "sys/stat.h" bewusst sein. Dies beinhaltet eine Reihe symbolischer Konstanten zum Setzen von Berechtigungsbits.

Beispiel: Öffnen einer Datei mit für den Benutzer aktivierten Lese-/Schreibberechtigungen

#include <fcntl.h>
#include <sys/stat.h>

open("Your/File/Path", O_RDWR | O_CREAT, S_IWUSR | S_IRUSR);

wo:

S_IWUSR // Sets the Users Write bit
S_IRUSR // Sets the Users Read bit

Diese Bibliothek enthält eine Reihe anderer, ich werde sie hier nicht alle auflisten, aber Sie können alles nachlesen hier .

Natürlich können Sie die Oktalwerte eingeben, um diese Bits zu setzen. Einige argumentieren jedoch möglicherweise, dass dies eine schlechte Codierungspraxis ist.

0
Levi Meston