12
votes

Vérification du succès de la FLE en C, Perror

Avec FLERITE Renvoie le nombre d'éléments réussis écrits dans le fichier, en disant:

if (!(fwrite(...))) {
    fprintf(stderr, "Failure");
    //perror(???)  I sometimes see code that says perror here and I don't know 
    //exactly what this does.
}


0 commentaires

5 Réponses :


15
votes

En bref, pas tout à fait. fwrite renvoie le nombre d'éléments écrits avec succès; Vous devez vérifier cela contre le nombre d'éléments que vous aviez destiné à écrire, c'est-à-dire. Ceux que vous avez transmis en argument à la f.

Qu'est-ce que vous avez fait des vérifications que certains éléments ont été écrits.

Voici une référence pour Perror .

interprète la valeur du global errono variable dans une chaîne et imprime cette chaîne à starr (standard Stream de sortie d'erreur, généralement le écran), facultatif qui le précède avec le message personnalisé spécifié dans Str. errno est une variable intégrale dont la valeur décrit la dernière erreur Produit par un appel à une bibliothèque une fonction. Les chaînes d'erreur produites par Perror dépend du développement plate-forme et compilateur. Si la Le paramètre STR n'est pas un pointeur nul, STR est imprimé suivi d'un colon (:) et un espace. Alors, si Str était un pointeur nul ou pas, le généré La description d'erreur est imprimée suivie par un personnage nouveau ('\ n'). perror devrait être appelé juste après l'erreur a été produit, sinon cela peut être écrasé dans les appels vers d'autres Fonctions.


1 commentaires

Il n'est pas nécessaire de comparer fwrite contre le nombre d'éléments si vous arrangez pour toujours l'appeler avec 1 élément de taille len . Ensuite, les valeurs de retour possibles ne sont que de 0 et 1, avec 0 indiquant toute défaillance et 1 indiquant le succès.



2
votes

Votre code pourrait ne pas vérifier correctement les erreurs. Utilisez

if (fwrite(ptr, size, num, f) != num) {
    // An error occurred, handle it somehow
}


1 commentaires

@mctylr: faux. fwrite ne peut pas gérer eagain ou eintr du tout. Ils définiront l'indicateur d'erreur du flux, et il n'ya aucun moyen de reprendre l'écriture sans que les données perdus ou en double (due à la ne pas connaître l'état du tampon). Si vous souhaitez utiliser des signaux d'interruption ou souhaitez configurer un fichier en tant que non bloque, Stdio n'est généralement pas utilisable.



0
votes

de la page homme Linux de fwrite

Fread () et fwrite () renvoient le nombre d'articles lus avec succès ou écrit (c'est-à-dire pas le nombre de caractères). Si une erreur se produit, ou Le bout de fichier est atteint, la valeur de retour est un nombre d'éléments court (ou zéro).

Vous devez donc comparer avec quelle est la valeur de retour attendue.

Dans de nombreux cas, vous devrez peut-être rechercher errno égal à eagain ou eintr , auquel cas tu veux normalement Réessayez la demande d'écriture, tandis que dans d'autres cas, vous souhaitez gérer des écrires courts gracieusement.

pour fwrite, sur un écrit court (où moins de vos données complètes a été écrit) Vous pouvez vérifier Feof () et / ou FERROR () pour voir si le flux retourne et fin. -File, EOF, comme si un tuyau était fermé ou si le flux a son drapeau de l'inducteur d'erreur.


2 commentaires

Voir mon commentaire sur votre autre commentaire. Des réessayer comme vous dites entraîneront une défaillance répétée et / ou une corruption de données.


Oui, je l'ai fait Bork, et j'ai frappé mon erreur d'origine. Un programme peut tenter d'appeler fwrite () après avoir appelé eplearerr () en toute sécurité, vérifiant à nouveau pour une erreur continue / défaillance / EOF, dans ma compréhension.



0
votes
STRERROR(3)            FreeBSD Library Functions Manual            STRERROR(3)

NAME
     perror, strerror, strerror_r, sys_errlist, sys_nerr — system error mes‐
     sages

LIBRARY
     Standard C Library (libc, -lc)

SYNOPSIS
     #include <stdio.h>

     void
     perror(const char *string);

     ...

DESCRIPTION
     ...

     The perror() function finds the error message corresponding to the cur‐
     rent value of the global variable errno (intro(2)) and writes it, fol‐
     lowed by a newline, to the standard error file descriptor.  If the argu‐
     ment string is non‐NULL and does not point to the null character, this
     string is prepended to the message string and separated from it by a
     colon and space (“: ”); otherwise, only the error message string is
     printed.

...

STANDARDS
     The perror() and strerror() functions conform to ISO/IEC 9899:1999
     (“ISO C99”).  ...

0 commentaires

2
votes

Vous pouvez également utiliser explic_fwrite () code>, expliquer_errno_fwrite code>, ... à partir de libexplain code>.

Le page explique: p>

La fonction wedlook_fwrite code> est utilisée pour obtenir une explication d'une erreur renvoyée par l'appel du système fwrite (3) code> appel. Le moins que le message contiendra est la valeur de strError (errno) code>, mais généralement, il fera beaucoup mieux et indiquer la cause sous-jacente plus en détail. Strong> p>

La variable Global Erno sera utilisée pour obtenir la valeur d'erreur à décoder. P>

Cette fonction est destinée à être utilisée de manière similaire à celle de l'exemple suivant (la page man ici, comme indiqué correctement par @Puchu dans le commentaire ci-dessous. J'ai corrigé le code pour résoudre le problème): P>

if (fwrite(ptr, size, nmemb, fp) < nmemb)
{
    fprintf(stderr, "%s\n", explain_fwrite(ptr, size, nmemb, fp));
    exit(EXIT_FAILURE);
}


2 commentaires

fwrite retourne taille_t . taille_t est une valeur non signée. Il n'est pas possible de <0 .


@puchu: merci. Tu as raison. La page man était tort. S'il vous plaît voir la réponse corrigée.