IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

C Discussion :

Erreur de segmentation après affichage d'un tableau d'entier


Sujet :

C

  1. #1
    Membre à l'essai
    Inscrit en
    Février 2004
    Messages
    40
    Détails du profil
    Informations forums :
    Inscription : Février 2004
    Messages : 40
    Points : 18
    Points
    18
    Par défaut Erreur de segmentation après affichage d'un tableau d'entier
    Bonsoir tout le monde
    Avant que vous ne continuez la lecture du code, je tiens à vous dire que j'ai déjà lu le tutoriel sur les pointeurs en C et C++ de son auteur CGI sur développez.com et j'ai fait de mon mieux .
    En fait, j'ai un fichier nommé share_application_TCB.C où est définie la structure

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    typedef struct{
    	int version; 		//kernel version
    	int sub_version;	//sub version
    	int ttcb_extentions;	//TTCB enabled?
    	int number_of_system_machines; //number of machines
    	int* TCBneighlist ; // list of TTCB neighbors
    	int TCBlenneighlist; // longueur de la liste
    }
    tcb_kernel_info_t;
    J'ai également un autre fichier nommé tcb_module.C (ici j'utilise l'API du kernel) où j'ai déclaré deux variables globales et une fonction decideau sein delaquelle je modifie les valeurs des variables globales

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    cb_kernel_info_t	kern_info;	// la structure à modifier
    int neighlist[20]; //tab intermediaire pour éviter erreurs de segmentations
    void TTCBdecide(int fifo, decide_in_t *in)
    {
     
     
    	// Au sein d'une boucle for
    			tailleEid = sscanf (existingID,"%d",&neighlist[j]);
    			kern_info.TCBneighlist=neighlist;
    			kern_info.TCBlenneighlist=j+1;
    			out.test=kern_info.TCBneighlist[j];
    }
    Enfin, au sein du fichier ttcbneighborhood.C 'essaie d'effectuer l'opération d'affichage du contenu krn_info.TCBneighlist[j] mais je me confronte à une erreur de segmentation que je n'arrive pas à expliquer.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    int main()
    {
     
    	//for kernel info 29_12_05
    	tcb_kernel_info_t krn_info;
    	int ret ;
    	int number_of_machines ;
    	int lenneighlist; // longuer du tableau des id
    	int k;
     
    	decide(&descriptor, outp.tag, &outd) //appel de la fonction decide qui met à jour la variable krn_info
    	//for kernel info 29_12_05
     
    	ret = getTCBKernelInfo(&descriptor, &krn_info); //j'appelle la fonction getTCBKernelInfo qui retourne la structure krn_info
     
    	if (ret < 0){
    		closeTCBConnection(&descriptor);
    		printTCBerror(ret);
    		printf("On getting TTCB kernel info...\n");
    		exit(1);
    	}
     
    	lenneighlist=krn_info.TCBlenneighlist;
    	printf ("Kernel Info : Le nombre d'entités impliquées est %d \n ",lenneighlist);
     
    	for (k=0;k<lenneighlist;k++)
    	printf ("Agreement Kernel Info : L'entité est %d \n ",krn_info.TCBneighlist[j]);
    }
    Quelqu'un aurait-il- une idée et pourquoi printf me génère l'erreur de segmentation? Merci beaucoup de votre aide

  2. #2
    Expert éminent sénior
    Avatar de Skyounet
    Homme Profil pro
    Software Engineer
    Inscrit en
    Mars 2005
    Messages
    6 380
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 37
    Localisation : Etats-Unis

    Informations professionnelles :
    Activité : Software Engineer
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Mars 2005
    Messages : 6 380
    Points : 13 380
    Points
    13 380
    Par défaut
    Sans la fonction getTCBKernelInfo qui est cense remplir la structure on ne pourra pas t'aider. Amoins que tu n'ais pas le corps de cette fonction (je ne sais pas si c'est une fonction de l'API)
    Introduction à Silverlight 4 (new) ; Localisation d'une application Silverlight (new) ;
    Mon espace perso[/B]

    La connaissance s’acquiert par l’expérience, tout le reste n’est que de l’information. Albert Einstein[/SIZE]

  3. #3
    Membre à l'essai
    Inscrit en
    Février 2004
    Messages
    40
    Détails du profil
    Informations forums :
    Inscription : Février 2004
    Messages : 40
    Points : 18
    Points
    18
    Par défaut
    En fait, c'est juste la fonction decide qui modifie le contenu du tableau , voici le code de la fonction getTCBKernelInfo :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    int getTCBKernelInfo(descriptor_t * descriptor,tcb_kernel_info_t* kern_inf){
     
    	int ret;
     
    	ret = call_tcb(get_kernel_info, descriptor, NULL, (tcb_kernel_info_t*)kern_inf, 0, sizeof(tcb_kernel_info_t)) ;
     
    	if (ret) return ret;
    	return 0;
    }
    En fait, c'est pas moi qui a tout codé, c'est un code libre en C que je suis entrain de modifier.

  4. #4
    Expert éminent sénior
    Avatar de Skyounet
    Homme Profil pro
    Software Engineer
    Inscrit en
    Mars 2005
    Messages
    6 380
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 37
    Localisation : Etats-Unis

    Informations professionnelles :
    Activité : Software Engineer
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Mars 2005
    Messages : 6 380
    Points : 13 380
    Points
    13 380
    Par défaut
    Quelle est au juste la fonction qui rempli la structure kern_inf : : :
    Parce que apparamment la segfault vient du fait que ton tableau ben y'a rien dedans et meme que le tableau n'est pas alloué
    Introduction à Silverlight 4 (new) ; Localisation d'une application Silverlight (new) ;
    Mon espace perso[/B]

    La connaissance s’acquiert par l’expérience, tout le reste n’est que de l’information. Albert Einstein[/SIZE]

  5. #5
    Membre à l'essai
    Inscrit en
    Février 2004
    Messages
    40
    Détails du profil
    Informations forums :
    Inscription : Février 2004
    Messages : 40
    Points : 18
    Points
    18
    Par défaut
    l'instruction de la fonction decide
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    kern_info.TCBneighlist=neighlist ; //neighlist déclaré tableau de 20entiers
    n'est pas suffisante ? il faut passer obligatoirement par malloc?

  6. #6
    Expert éminent sénior
    Avatar de Skyounet
    Homme Profil pro
    Software Engineer
    Inscrit en
    Mars 2005
    Messages
    6 380
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 37
    Localisation : Etats-Unis

    Informations professionnelles :
    Activité : Software Engineer
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Mars 2005
    Messages : 6 380
    Points : 13 380
    Points
    13 380
    Par défaut
    Citation Envoyé par NeilaK
    l'instruction de la fonction decide
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    kern_info.TCBneighlist=neighlist ; //neighlist déclaré tableau de 20entiers
    n'est pas suffisante ? il faut passer obligatoirement par malloc?
    Arf si j'avais pas vu.

    Une question

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     
    for (k=0;k<lenneighlist;k++)
       printf ("Agreement Kernel Info : L'entité est %d \n ",krn_info.TCBneighlist[j]);
    dans la boucle c'est k et on affiche [j]
    Erreur de frappe ou erreur tout court?
    Introduction à Silverlight 4 (new) ; Localisation d'une application Silverlight (new) ;
    Mon espace perso[/B]

    La connaissance s’acquiert par l’expérience, tout le reste n’est que de l’information. Albert Einstein[/SIZE]

  7. #7
    Modérateur
    Avatar de ggnore
    Profil pro
    Inscrit en
    Juillet 2004
    Messages
    2 472
    Détails du profil
    Informations personnelles :
    Âge : 45
    Localisation : France

    Informations forums :
    Inscription : Juillet 2004
    Messages : 2 472
    Points : 4 029
    Points
    4 029
    Par défaut
    S'il n'y a pas d'erreur à la compilation, c'est que j est une variable globale
    Toutes les vertus des hommes se perdent dans l’intérêt comme les fleuves se perdent dans la mer.
    N'oubliez pas de consulter les FAQ Linux et les cours et tutoriels Linux

  8. #8
    Membre à l'essai
    Inscrit en
    Février 2004
    Messages
    40
    Détails du profil
    Informations forums :
    Inscription : Février 2004
    Messages : 40
    Points : 18
    Points
    18
    Par défaut
    j ne pose pas deproblèmen je l'ai déjà corrigé mais l'erreur de segmentation persiste toujours

  9. #9
    Rédacteur/Modérateur
    Avatar de Trap D
    Profil pro
    Inscrit en
    Septembre 2003
    Messages
    4 942
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Septembre 2003
    Messages : 4 942
    Points : 6 498
    Points
    6 498
    Par défaut
    20 entiers : est-ce suffisant, je n'ai pas vu de test sur kern_info.TCBlenneighlist.
    "La haine seule fait des choix" - Koan Zen
    "Il ne faut pas être meilleur que les autres, il faut être meilleur que soi." Albert Jacquard
    "Ceux qui savent où ils ont posé leur parapluie ne sont pas alcooliques." - pgibonne.
    Faites du Prolog, ça vous changera les idées !
    Ma page Prolog
    Mes codes sources commentés

    Mon avatar : La Madeleine à la veilleuse de Georges de La Tour

  10. #10
    Rédacteur

    Avatar de gege2061
    Femme Profil pro
    Administrateur de base de données
    Inscrit en
    Juin 2004
    Messages
    5 840
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Âge : 40
    Localisation : France

    Informations professionnelles :
    Activité : Administrateur de base de données

    Informations forums :
    Inscription : Juin 2004
    Messages : 5 840
    Points : 11 625
    Points
    11 625
    Par défaut Re: Erreur de segmentation après affichage d'un tableau d'en
    Bonjour,
    Citation Envoyé par NeilaK
    share_application_TCB.C
    L'extension doit être .c en minuscule sinon, si tu utilise gcc, il appellera le compilateur C++

  11. #11
    Membre à l'essai
    Inscrit en
    Février 2004
    Messages
    40
    Détails du profil
    Informations forums :
    Inscription : Février 2004
    Messages : 40
    Points : 18
    Points
    18
    Par défaut
    20 entiers c'est largement suffisant, la taille du tableau n'est pas censée les dépasser, toutefois, tu as raison, merci pour la remarque, il va falloir que j'ajoute un test. Mais l'erreur de segmentation persiste toujours

  12. #12
    Expert éminent sénior

    Avatar de fearyourself
    Homme Profil pro
    Ingénieur Informaticien Senior
    Inscrit en
    Décembre 2005
    Messages
    5 121
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : Etats-Unis

    Informations professionnelles :
    Activité : Ingénieur Informaticien Senior
    Secteur : Industrie

    Informations forums :
    Inscription : Décembre 2005
    Messages : 5 121
    Points : 11 877
    Points
    11 877
    Par défaut
    Commence par mettre les champs de ta structure à des valeurs par défaut et vérifie si les valeurs ont été correctement modifié avant l'affichage...

    ie: est-ce que le pointeur kern_info.TCBneighlist a été correctement changé pour pointer vers neighlist

    Jc

  13. #13
    Rédacteur/Modérateur
    Avatar de Trap D
    Profil pro
    Inscrit en
    Septembre 2003
    Messages
    4 942
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Septembre 2003
    Messages : 4 942
    Points : 6 498
    Points
    6 498
    Par défaut
    J'ai une petite remarque sur ce code :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    int getTCBKernelInfo(descriptor_t * descriptor,tcb_kernel_info_t* kern_inf){
     
       int ret;
     
       ret = call_tcb(get_kernel_info, descriptor, NULL, (tcb_kernel_info_t*)kern_inf, 0, sizeof(tcb_kernel_info_t)) ;
     
       if (ret) return ret;
       return 0;
    }
    if (ret) return ret;
    return 0;

    Si tout le code est du même acabit, il faudrait que tu le postes en entier car on pourrait avoir des surprises.
    "La haine seule fait des choix" - Koan Zen
    "Il ne faut pas être meilleur que les autres, il faut être meilleur que soi." Albert Jacquard
    "Ceux qui savent où ils ont posé leur parapluie ne sont pas alcooliques." - pgibonne.
    Faites du Prolog, ça vous changera les idées !
    Ma page Prolog
    Mes codes sources commentés

    Mon avatar : La Madeleine à la veilleuse de Georges de La Tour

  14. #14
    Membre à l'essai
    Inscrit en
    Février 2004
    Messages
    40
    Détails du profil
    Informations forums :
    Inscription : Février 2004
    Messages : 40
    Points : 18
    Points
    18
    Par défaut
    Vous remarquez qu'au sein de la fonction decide, j'ai cette ligne de code qui normalement (puisque je suis au sein de la boucle for) va mettre dans la dernière case du tableau la dernière valeur de l'entité.
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    out.test=kern_info.TCBneighlist[j];
    Par la suite , au sein du fichier TTCBneighborhood.c, après l'appel du decide, j'ai ajouté ce code
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    decide(&descriptor, outp.tag, &outd) //appel de la fonction decide qui met à jour la variable krn_info 
    printf("La valeur de la dernière case de kern_info.TCBneighlist[j] est %d",outd.test);
    Et l'affichage a correctement fonctionné, c'est à dire que le tableau kern_info.TCBneighlist contient effectivement ce qu'il doit contenir, ce qui veut dire que le pointeur kern_info.TCBneighlist a été correctement changé pour pointer vers neighlist.
    Une petite remarque pour Trap D : je n'ai pas écris tout le code moi même, c'est un code libre d'un compopsant logiciel formé par des modules kernel écrits en C. Mon rôle consiste à le modifier pour qu'il prenne en charge un protocole que j'ai défini, je ne peux pas donc tout vérifier.

  15. #15
    Expert éminent sénior

    Avatar de fearyourself
    Homme Profil pro
    Ingénieur Informaticien Senior
    Inscrit en
    Décembre 2005
    Messages
    5 121
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : Etats-Unis

    Informations professionnelles :
    Activité : Ingénieur Informaticien Senior
    Secteur : Industrie

    Informations forums :
    Inscription : Décembre 2005
    Messages : 5 121
    Points : 11 877
    Points
    11 877
    Par défaut
    Je vais reprendre à zéro, c'est ici que ton programme fait une erreur de segmentation:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     
       for (k=0;k<lenneighlist;k++)
       printf ("Agreement Kernel Info : L'entité est %d \n ",krn_info.TCBneighlist[k]); //modification du j en k
    Change le en et donne nous la sortie s'il y a une erreur:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
       for (k=0;k<20;k++)
           printf ("Agreement Kernel Info : L'entité est %d \n ",krn_info.TCBneighlist[k]); 
    //modification du j en k
    Chose aussi à tester:

    Recompile tous tes fichiers, c'est source d'erreurs si tu as modifié une structure...

  16. #16
    Membre à l'essai
    Inscrit en
    Février 2004
    Messages
    40
    Détails du profil
    Informations forums :
    Inscription : Février 2004
    Messages : 40
    Points : 18
    Points
    18
    Par défaut
    j'ai essaye le code
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    for (k=0;k<20;k++) 
       printf ("Agreement Kernel Info : L'entité est %d \n ",krn_info.TCBneighlist[k]); //modification du j en k
    mais l'erreur persiste toujours. De toute façon, en affichant la valeur de lenneiglist avec
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    lenneighlist=krn_info.TCBlenneighlist; 
       printf ("Kernel Info : Le nombre d'entités impliquées est %d \n ",lenneighlist);
    j'obtient une valeur tout à fait correcte
    Par contre en essayant d'afficher l'adresse mémoire du pointeur avec
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    for (k=0;k<lenneighlist;k++) 
    printf ("Agreement Kernel Info : L'entité est %d \n ",&krn_info.TCBneighlist[k]);
    on m'affiche la plupart du temps la valeur négative -526285056 (2 fois pour 2 entités) . J'ai exécuté la même instruction plusieurs fois, il m'a affiché une fois les valeurs (0 et 4 dans le cas de deux entités.) Je ne sais pas si ceci peut servir comme indice

  17. #17
    Expert éminent sénior

    Avatar de fearyourself
    Homme Profil pro
    Ingénieur Informaticien Senior
    Inscrit en
    Décembre 2005
    Messages
    5 121
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : Etats-Unis

    Informations professionnelles :
    Activité : Ingénieur Informaticien Senior
    Secteur : Industrie

    Informations forums :
    Inscription : Décembre 2005
    Messages : 5 121
    Points : 11 877
    Points
    11 877
    Par défaut
    Sans voir tout le code, il est difficile de déceler l'endroit où il y a une erreur...

    Par contre en essayant d'afficher l'adresse mémoire du pointeur avec
    Il faut utiliser %p pour afficher l'adresse d'un pointeur...

    - Affiche la valeur du pointeur neighlist et la valeur du pointeur krn_info.TCBneighlist, vérifie qu'ils sont identiques

    - Es-tu sûr que c'est à cet endroit que se pose le problème, comment le sais-tu? Ajoute un printf("Fin de l'affichage\n"); juste en dessous pour voir...

    - As-tu tout recompilé? Enlève tous les .o pour être sur...

    - Mets ton code sur le web quelque part pour qu'on y jette un coup d'oeil...


    Jc

  18. #18
    Expert éminent sénior
    Avatar de Emmanuel Delahaye
    Profil pro
    Retraité
    Inscrit en
    Décembre 2003
    Messages
    14 512
    Détails du profil
    Informations personnelles :
    Âge : 67
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Retraité

    Informations forums :
    Inscription : Décembre 2003
    Messages : 14 512
    Points : 20 985
    Points
    20 985
    Par défaut
    Citation Envoyé par fearyourself
    Il faut utiliser %p pour afficher l'adresse d'un pointeur...
    Plus précisément, il faut "%p" et (void*) pour afficher une adresse ou la valeur d'un pointeur.
    Pas de Wi-Fi à la maison : CPL

  19. #19
    Membre à l'essai
    Inscrit en
    Février 2004
    Messages
    40
    Détails du profil
    Informations forums :
    Inscription : Février 2004
    Messages : 40
    Points : 18
    Points
    18
    Par défaut
    Vous remarquerez que j'utilise 3 fichiers
    1- 1 fichier où est définie la structure
    2- un fichier tcb_module.c qui est un peu particulier parceque c'est un module Kernel. A chaque fois que j'effectue la moindre modification dans ce fichier, je recompile le tout (las .o sont tous reconstruit). Comme c'est un module kernel, la fonction prrintf ne marche pas (n'affiche rien", par contre, je sais que la valeur du pointeur neighlist et la valeur du pointeur krn_info.TCBneighlist sont identiques parceque j'ai récupéré la valeur de krn_info.TCBneighlist[k] au sein de decide puis et je l'ai affcichée au sein du troisième fichier et elle est correcte
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    decide(&descriptor, outp.tag, &outd) //appel de la fonction decide qui met à jour la variable krn_info 
    printf("La valeur de la dernière case de kern_info.TCBneighlist[j] est %d",outd.test);
    3- le troisième fichier appelle les services du kernel (notamment la fonction decide) et doit récupérer les résultats
    Les trois fichiers sont un peu compliqués mais je vais vous les procurer
    Merci

  20. #20
    Expert éminent sénior
    Avatar de Emmanuel Delahaye
    Profil pro
    Retraité
    Inscrit en
    Décembre 2003
    Messages
    14 512
    Détails du profil
    Informations personnelles :
    Âge : 67
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Retraité

    Informations forums :
    Inscription : Décembre 2003
    Messages : 14 512
    Points : 20 985
    Points
    20 985
    Par défaut
    Citation Envoyé par NeilaK
    2- un fichier tcb_module.c qui est un peu particulier parceque c'est un module Kernel. <...> Comme c'est un module kernel, la fonction printf ne marche pas <...>
    Huh! Tu parles d'un module kernel Linux, par exemple ? Il est absolument interdit d'utiliser printf() en mode kernel. Il faut utiliser printk().

    Attention, le mode kernel, c'est pas pour les débutants. Il faut vraiment savoir ce que l'on fait...
    Pas de Wi-Fi à la maison : CPL

Discussions similaires

  1. erreur lors de l'affichage d'un tableau
    Par romrom12 dans le forum Langage
    Réponses: 6
    Dernier message: 30/04/2012, 23h05
  2. Réponses: 11
    Dernier message: 29/11/2011, 14h15
  3. erreur d'affichage pour on tableau de bord
    Par nidhal fekih dans le forum Flash
    Réponses: 0
    Dernier message: 29/07/2008, 21h07
  4. Réponses: 5
    Dernier message: 04/11/2007, 13h39

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo