Assignment Chef icon Assignment Chef
All German tutorials

Programming lesson

Checksum-Berechnung in C: 8-, 16- und 32-Bit-Prüfsummen für ASCII-Dateien

Lerne in diesem Tutorial, wie du ein C-Programm schreibst, das die 8-, 16- und 32-Bit-Checksumme für eine ASCII-Textdatei berechnet. Schritt-für-Schritt-Anleitung mit Codebeispielen und Tipps zur Fehlerbehandlung.

Checksumme berechnen C 8 Bit Checksumme 16 Bit Checksumme 32 Bit Checksumme C Programmierung Tutorial Prüfsumme ASCII Datei Kommandozeilenargumente C Datei einlesen C Checksumme in C programmieren Datenintegrität Prüfsumme C Übungsaufgabe Checksumme Bit-Manipulation C Checksumme ohne Überlauf Fehlererkennung mit Checksumme C Projekt für Anfänger Checksumme in der Praxis

Einführung: Warum Checksummen wichtig sind

Checksummen sind ein grundlegendes Werkzeug der Datenintegritätsprüfung. Ob beim Download von Dateien, bei der Übertragung über Netzwerke oder in der Speicherung – eine einfache Prüfsumme hilft, Fehler zu erkennen. In diesem Tutorial lernst du, wie du ein C-Programm schreibst, das aus einer ASCII-Textdatei eine 8-, 16- oder 32-Bit-Checksumme berechnet. Das Programm wird über die Kommandozeile gesteuert und gibt die Ergebnisse formatiert aus. Dieses Projekt entspricht typischen Aufgaben aus der Systemprogrammierung und ist ideal, um deine Fähigkeiten in C zu vertiefen.

Stell dir vor, du entwickelst eine App, die Spielstände eines Turniers speichert. Eine Checksumme stellt sicher, dass die Daten nicht korrupt sind. Oder in der Finanzwelt: Bei Überweisungen wird eine Prüfsumme verwendet, um Tippfehler zu vermeiden. Genau solche Konzepte lernst du hier.

Ziel des Programms

Dein Programm soll zwei Kommandozeilenparameter entgegennehmen: den Dateinamen einer ASCII-Textdatei und die gewünschte Checksummen-Größe (8, 16 oder 32 Bit). Es öffnet die Datei, gibt den Inhalt auf der Konsole aus, berechnet die Prüfsumme und gibt sie im Format %2d bit checksum is %8lx for all %4d chars aus. Bei ungültiger Größe wird eine Fehlermeldung auf STDERR ausgegeben.

Schritt 1: Kommandozeilenparameter einlesen

Der erste Schritt ist das Einlesen der Argumente. In C geschieht das über argc und argv. Prüfe, ob genau zwei Argumente übergeben wurden. Das zweite Argument (die Checksummen-Größe) muss in eine ganze Zahl umgewandelt werden. Ist sie nicht 8, 16 oder 32, gib eine Fehlermeldung aus und beende das Programm.

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

int main(int argc, char *argv[]) {
    if (argc != 3) {
        fprintf(stderr, "Usage: %s inputFile.txt checksumSize\n", argv[0]);
        return 1;
    }
    int checksumSize = atoi(argv[2]);
    if (checksumSize != 8 && checksumSize != 16 && checksumSize != 32) {
        fprintf(stderr, "Valid checksum sizes are 8, 16, or 32\n");
        return 1;
    }
    // ...
}

Schritt 2: Datei öffnen und Inhalt ausgeben

Öffne die Datei im Lesemodus. Lese Zeichen für Zeichen (oder blockweise) und gib sie auf STDOUT aus. Achte darauf, dass du insgesamt 80 Zeichen pro Zeile ausgibst – das ist ein typisches Format für Textdateien. Zähle dabei die Anzahl der gelesenen Zeichen, denn du benötigst sie für die Ausgabe der Checksumme.

FILE *file = fopen(argv[1], "r");
if (!file) {
    fprintf(stderr, "Error opening file\n");
    return 1;
}
int ch;
int charCount = 0;
while ((ch = fgetc(file)) != EOF) {
    putchar(ch);
    charCount++;
}
rewind(file); // Zurücksetzen für Checksum-Berechnung

Schritt 3: Checksumme berechnen

Die Checksumme ist eine laufende Summe aller Zeichenwerte (als unsigned int). Wichtig: Es gibt keinen Überlauf – die Summe wird einfach in einer Variable der entsprechenden Größe gehalten. Für 8 Bit verwendest du unsigned char, für 16 Bit unsigned short, für 32 Bit unsigned int. Du kannst aber auch immer eine 32-Bit-Variable verwenden und später maskieren.

Lese die Datei erneut Zeichen für Zeichen und addiere den Wert jedes Zeichens zur Summe. Nachdem alle Zeichen verarbeitet wurden, musst du die Summe ggf. auf die gewünschte Bitbreite reduzieren:

  • 8 Bit: checksum & 0xFF
  • 16 Bit: checksum & 0xFFFF
  • 32 Bit: checksum & 0xFFFFFFFF

Zusätzlich wird bei 16 und 32 Bit eine Padding-Information benötigt. Die Padding-Bytes werden in der Ausgabe als Hex-Zahl angehängt. Die genaue Berechnung des Paddings ist in der Aufgabenstellung beschrieben: Es werden so viele 'XX'-Bytes angehängt, dass die Gesamtzahl der Zeichen ein Vielfaches der Checksummen-Größe in Bytes ist. Du kannst das Padding als separate Variable berechnen und später ausgeben.

unsigned int checksum = 0;
int ch;
while ((ch = fgetc(file)) != EOF) {
    checksum += (unsigned char)ch;
}
// Reduzieren auf gewünschte Bitbreite
unsigned int result;
switch (checksumSize) {
    case 8:  result = checksum & 0xFF; break;
    case 16: result = checksum & 0xFFFF; break;
    case 32: result = checksum & 0xFFFFFFFF; break;
}
// Padding berechnen (vereinfacht):
int padding = (checksumSize/8) - (charCount % (checksumSize/8));
if (padding == (checksumSize/8)) padding = 0;
// Ausgabe
printf("%2d bit checksum is %8lx for all %4d chars\n", checksumSize, result, charCount);

Schritt 4: Formatierte Ausgabe

Die Ausgabe muss exakt dem geforderten Format entsprechen. Verwende printf mit den Platzhaltern %2d für die Checksummen-Größe, %8lx für die Checksumme (als Hexadezimal, 8 Stellen breit) und %4d für die Zeichenanzahl. Vergiss nicht, nach dem Dateiinhalt eine neue Zeile einzufügen, falls nötig.

Beispiel für eine korrekte Ausgabe:

This is a test.
 8 bit checksum is       6b for all   12 chars

Schritt 5: Fehlerbehandlung und Testen

Dein Programm sollte robust sein. Behandle folgende Fälle:

  • Datei existiert nicht oder kann nicht geöffnet werden → Fehlermeldung auf STDERR.
  • Ungültige Checksummen-Größe → Fehlermeldung auf STDERR.
  • Leere Datei → Checksumme ist 0, Zeichenanzahl 0.

Teste dein Programm mit den beigelegten Testdateien (i1.txt bis i5.txt). Die erwarteten Checksummen findest du in der Aufgabenstellung. Verwende das Bash-Skript basetest.sh, um deine Ausgabe mit der Referenz zu vergleichen.

Häufige Fehler und Tipps

  • Vergiss nicht, die Datei nach dem ersten Durchlauf zurückzusetzen (rewind) oder erneut zu öffnen.
  • Achte auf den Unterschied zwischen unsigned char und char – Zeichen können negativ sein, daher immer unsigned char verwenden.
  • Der Zeilenvorschub (LF, 0x0A) ist Teil der Checksumme. Zähle ihn mit.
  • Die Padding-Berechnung kann knifflig sein. Studiere die Beispiele in der Aufgabenstellung genau.

Zusammenfassung

Du hast gelernt, wie man ein C-Programm schreibt, das eine 8-, 16- oder 32-Bit-Checksumme für eine ASCII-Datei berechnet. Dieses Projekt festigt Grundlagen der Dateiverarbeitung, Kommandozeilenargumente und Bit-Manipulation. Solche Checksummen werden in vielen Bereichen eingesetzt, von der Netzwerkkommunikation bis zur Spieleentwicklung. Probiere es selbst aus und passe das Programm an – vielleicht erweiterst du es um eine Überprüfungsfunktion oder eine grafische Oberfläche.