7 Stimmen

Mögliches Problem mit C-Standard-Malloc'ing-Zeichen

Als Antwort auf einen Kommentar zu einer anderen Antwort von mir ici habe ich gefunden, was ich denke Mai eine Lücke im C-Standard sein (c1x, die früheren habe ich nicht überprüft, und ja, ich weiß, dass es unglaublich unwahrscheinlich ist, dass ich allein unter allen Bewohnern der Erde einen Fehler im Standard gefunden habe). Informationen folgen:

  1. In Abschnitt 6.5.3.4 ("The sizeof operator") Absatz 2 heißt es "The sizeof operator yields the size (in bytes) of its operand" .
  2. In Absatz 3 dieses Abschnitts heißt es: "When applied to an operand that has type char, unsigned char, or signed char, (or a qualified version thereof) the result is 1" .
  3. Abschnitt 7.20.3.3 beschreibt void *malloc(size_t sz) aber alles, was dort steht, ist "The malloc function allocates space for an object whose size is specified by size and whose value is indeterminate" . Es wird überhaupt nicht erwähnt, welche Einheiten für das Argument verwendet werden.
  4. Anhang E beginnt die 8 ist die Minimum Wert für CHAR_BIT so dass die Zeichen mehr als ein Byte lang sein können.

Meine Frage ist einfach die folgende:

In einer Umgebung, in der ein Zeichen 16 Bit breit ist, wird malloc(10 * sizeof(char)) 10 Zeichen (20 Byte) oder 10 Byte zuweisen? Punkt 1 scheint auf Ersteres hinzudeuten, Punkt 2 auf Letzteres.

Hat jemand mit mehr C-Standard-Kenntnissen als ich eine Antwort auf diese Frage?

16voto

Chris Lutz Punkte 69879

In einem 16-Bit char Umwelt malloc(10 * sizeof(char)) wird 10 % zuweisen char s (10 Bytes), denn wenn char 16 Bits ist, dann definiert diese Architektur/Implementierung ein Byte als 16 Bits. A char ist kein Oktett, sondern ein Byte. Auf älteren Computern kann dies größer sein als die 8-Bit de-facto Standard, den wir heute haben.

Es folgt der entsprechende Abschnitt aus der C-Norm:

3.6 Begriffe, Definitionen und Symbole

Byte - adressierbare Einheit des Datenspeichers, die groß genug ist, um ein beliebiges Element des Basiszeichensatzes der Ausführungsumgebung zu speichern...

ANMERKUNG 2 - Ein Byte besteht aus einer zusammenhängenden Folge von Bits, deren Anzahl von der Implementierung festgelegt wird.

2voto

Michael Burr Punkte 320591

In der C99-Norm ist die strenge Korrelation zwischen Bytes festgelegt, char und die Objektgröße ist in 6.2.6.1/4 "Darstellungen von Typen - Allgemein" angegeben:

Werte, die in Nicht-Bit-Feld-Objekten jedes anderen Objekttyps gespeichert werden, bestehen aus n × CHAR_BIT Bits, wobei n ist die Größe eines Objekts dieses Typs in Bytes. Der Wert kann in ein Objekt des Typs unsigned char [n] (z.B. durch memcpy); die resultierende Menge von Bytes wird als Objektrepräsentation des Wertes bezeichnet.

Im C++-Standard ist die gleiche Beziehung in 3.9/2 "Typen" angegeben:

Für jedes Objekt (mit Ausnahme von Unterobjekten der Basisklasse) des POD-Typs T, unabhängig davon, ob das Objekt einen gültigen Wert des Typs T enthält oder nicht, können die zugrunde liegenden Bytes (1.7), aus denen das Objekt besteht, in ein Array von char oder unsigned char kopiert werden. Wird der Inhalt des Arrays von char oder unsigned char zurück in das Objekt kopiert, muss das Objekt anschließend seinen ursprünglichen Wert behalten.

In C90 scheint es keine explizit erwähnte Korrelation zu geben, aber zwischen der Definition eines Bytes, der Definition eines Zeichens und der Definition des sizeof Betreiber die Schlussfolgerung gezogen werden, dass ein char ist gleichbedeutend mit einem Byte.

Beachten Sie auch, dass die Anzahl der Bits in einem Byte (und die Anzahl der Bits in einer char ) ist implementierungsabhängig und muss streng genommen nicht 8 Bit betragen. Und onebyone weist in einem Kommentar an anderer Stelle darauf hin, dass DSPs in der Regel Bytes mit einer Anzahl von Bits haben, die nicht 8 ist.

Beachten Sie, dass in den RFCs und Standards der IETF im Allgemeinen (immer?) der Begriff "octect" anstelle von "byte" verwendet wird, um unmissverständlich klarzustellen, dass die Einheiten, von denen sie sprechen, genau 8 Bits haben - nicht mehr und nicht weniger.

1voto

twon33 Punkte 533

Sind die Einheiten von "size_t sz" nicht in der adressierbaren Einheit Ihrer Architektur enthalten? Ich arbeite mit einem DSP, dessen Adressen 32-Bit-Werten entsprechen, nicht Bytes. malloc(1) liefert mir einen Zeiger auf einen 4-Byte-Bereich.

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X