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 :

résoudre program received signal sigsegv segmentation fault


Sujet :

C++

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Invité
    Invité(e)
    Par défaut résoudre program received signal sigsegv segmentation fault
    Bonjour à tous !

    Je tente actuellement de créer un mini jeu vidéo en 3d à l'aide de la librairie ogre3d.
    Ce jeu est un minecraft-like, cela implique donc que le terrain est constitué de blocs.
    Mais, je peine actuellement sur l'algorithme d'affichage des blocs.

    En effet, j'enregistre actuellement le terrain dans des tableaux en 3 dimensions et, le terrain est divisé en 9 partie(chunk) contenant chacun un tableau de string de 10*32*10 (x,y,z) blocs. 32 étant la hauteur maximale du terrain pour le moment.

    Mon algorithme considère que un bloc n'est pas visible si au dessus, en dessous, à droite, à gauche, devant et derrière lui il y a un bloc.
    C'est extrêmement facile de faire une vérification à l'intérieur de chaque chunk mais, lorsque je me trouve sur les bords d'un des chunk il faut que je trouve celui à coté pour vérifier si le bloc à coté de celui-ci est vide ou non.
    J'ai donc un terrain constitué de cette façon :
    0 0 0
    0 0 0
    0 0 0

    Et pour éviter que des blocks s'affiche inutilement sur les bords du terrain en dessous des blocs visible, j'ai virtuellement entouré le terrain avec des chunks plein de cette façon :

    v v v
    v 0 0 0 v
    v 0 0 0 v
    v 0 0 0 v
    v v v
    Avec chaque chunk contenant un tableau de pointeurs vers les quatre chunk l'entourant.
    Mon problème survient lorsque je tente d'accéder pour la première fois à ce chunk virtuel.
    En débogage, j'obtiens l'erreur suivante :

    received signal sigsegv segmentation fault

    L'erreur survient lorsque a = 6079 ou 6080.
    À ce moment j'appel une méthode de la classe chunk pour tester ce qui ne vas pas.
    Toujours du côté débogage, l'érreur survient sur la méthode checkX(x=10, y=0, z=0) avec comme local variable : ch = 0x5.


    J'espère avoir bien expliqué...
    Voici le code :


    Main.cpp :
    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
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    #include <iostream>
    #include <vector>
     
    #include "planet.h"
    #include "./chunk.h"
     
     
    using namespace std;
     
    int main()
    {
        int a =0;
        planet *terrain = new planet();
        std::vector <Chunk *> chunks = terrain->getChunk();
     
        for(int v = 0; v < chunks.size(); v++){
            for(int i = 0; i < CHWIDTH; i++){
                for(int j = 0; j < CHHEIGHT; j++){
                    for(int k = 0; k < CHWIDTH; k++){
                        if(a >= 6079 && a < 6080){
                            if(chunks[v]->isVisible(i,j,k,1)){
                                cout << a << endl;
                                a++;
                            }
                        }else{
                            if(chunks[v]->isVisible(i,j,k)){
                                a++;
                            }
                        }
                    }
                }
            }
        }
        return 0;
    }
    </code>
    planet.h : 
    <code type="cpp">
    #ifndef PLANETE_H
    #define PLANETE_H
     
    #include <string>
     
    #include <vector>
     
    class Chunk;
     
    class planet
    {
    public:
        planet();
        virtual ~planet();
        std::vector <Chunk *> getChunk();
     
    private:
        int m_seed;
        std::string m_path;
        std::vector <Chunk *> m_Chunks;
    };
     
    #endif // PLANETE_H
    planet.cpp :
    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
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    #include <iostream>
    #include <string>
     
    #include "./ChunkGenerator.h"
    #include "./Chunk.h"
     
    #include "./planet.h"
     
    planet::planet()
    {
        for(int x = 0;x<3;x++)
        {
            for(int z = 0; z < 3; z++)
            {
                Chunk *ch = new Chunk();
                ch->setX(x);
                ch->setZ(z);
                m_Chunks.push_back(ch);
            }
        }
        //see m_ChunkList doc
        Chunk *ch = new Chunk(0,0);
        for(int x = 0;x<3;x++)
        {
            for(int z = 0; z < 3; z++)
            {
                if(x+1 < 3){
                    m_Chunks[x+z]->m_ChunkList.push_back(m_Chunks[x+3+z]);
                }else{
                    m_Chunks[x+z]->m_ChunkList.push_back(ch);
                }
                if(z-1 >= 0){
                    m_Chunks[x+z]->m_ChunkList.push_back(m_Chunks[x+z-1]);
                }else{
                    m_Chunks[x+z]->m_ChunkList.push_back(ch);
                }
                if(x-1 >= 0){
                    m_Chunks[x+z]->m_ChunkList.push_back(m_Chunks[x-3+z]);
                }else{
                    m_Chunks[x+z]->m_ChunkList.push_back(ch);
                }
                if(z+1 < 3){
                    m_Chunks[x+z]->m_ChunkList.push_back(m_Chunks[x+z+1]);
                }else{
                    m_Chunks[x+z]->m_ChunkList.push_back(ch);
                }
            }
        }
    }
    std::vector <Chunk *> planet::getChunk()
    {
        return m_Chunks;
    }
    planet::~planet()
    {
        //dtor
    }
    Chunk.h :
    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
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    #ifndef CHUNK_H
    #define CHUNK_H
     
    #include <string>
    #include <vector>
     
     
    #define CHWIDTH 10
    #define CHHEIGHT 32
     
    class planet;
     
    class Chunk
    {
        public:
            Chunk();
            Chunk(int x, int z);
            virtual ~Chunk();
            bool isVisible(int x, int y, int z);
            bool isVisible(int x, int y, int z, int a);
            void setBlockAt(std::string block, int x, int y, int z);
     
            int getX() {return m_x;}
            void setX(int val) {m_x = val;}
            int getZ() {return m_z;}
            void setZ(int val) {m_z = val;}
     
            std::string m_map[CHWIDTH][CHHEIGHT][CHWIDTH];
            std::vector <Chunk* > m_ChunkList;//Chunks around
            //0 to 3 in circular order start at x+1
        protected:
        private:
            int m_x;
            int m_z;
            std::string m_index;
     
            bool checkX(int x, int y, int z);
            bool checkY(int x, int y, int z);
            bool checkZ(int x, int y, int z);
            Chunk* getChunkAt(std::string index);
     
            bool freeAt(int x, int y, int z, Chunk* ch);
    };
     
    #endif // CHUNK_H
    Chunk.cpp :
    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
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    100
    101
    102
    103
    104
    105
    106
    107
    108
    109
    110
    111
    112
    113
    114
    115
    116
    117
    118
    119
    120
    121
    122
    123
    124
    #include "./Chunk.h"
    #include <iostream>
    #include <fstream>
     
    #include "./planet.h"
     
    Chunk::Chunk(){
        for(int x = 0; x < CHWIDTH; x++){
            for(int y = 0; y < CHHEIGHT; y++){
                for(int z = 0; z < CHWIDTH; z++){
                    m_map[x][y][z] = "a";
                }
            }
        }
    }
    Chunk::Chunk(int x, int z)
    {
        m_x = x;
        m_z = z;
        for(int x = 0; x < CHWIDTH; x++){
            for(int y = 0; y < CHHEIGHT; y++){
                for(int z = 0; z < CHWIDTH; z++){
                    m_map[x][y][z] = "a";
                }
            }
        }
    }
     
    Chunk::~Chunk()
    {
        for(int i = 0; i < 4; i++){
            delete m_ChunkList[i];
        }
    }
     
    bool Chunk::isVisible(int x, int y, int z){
        if(m_map[x][y][z].compare("") == 0){
            return false;
        }
        if(checkX(x+1, y, z) || checkX(x-1, y, z) ||
           checkY(x, y+1, z) || checkY(x, y-1, z) ||
           checkZ(x, y, z+1) || checkZ(x, y, z-1)){
                return true;
           }else{return false;}
    }
    bool Chunk::isVisible(int x, int y, int z, int a){
        if(m_map[x][y][z].compare("") == 0){
            return false;
        }
        Chunk* ch = m_ChunkList[2];
        std::cout << ch->getX() << std::endl;
        if(ch->m_map[0][y][z].compare("") == 0){
            std::cout << "0" << std::endl;
        }
        std::cout << "1" << std::endl;
    }
     
    bool Chunk::checkX(int x, int y, int z){
        if(x >= CHWIDTH){
            Chunk* ch = m_ChunkList[0];
            if(freeAt(0, y, z, ch)){return false;}
            else{return true;}
        }else if(x < 0){
            Chunk* ch = getChunkAt(std::string("x-1"));
            if(freeAt(CHWIDTH-1, y, z, ch)){return false;}
            else{return true;}
        }else{
            if(freeAt(x, y, z, this)){return false;}
            else{return true;}
        }
     
    }
    bool Chunk::checkZ(int x, int y, int z){
        if(z >= CHWIDTH){
            Chunk* ch = getChunkAt(std::string("z+1"));
            if(freeAt(x, y, 0, ch)){return false;}
            else{return true;}
        }else if(x < 0){
            Chunk* ch = getChunkAt(std::string("z-1"));
            if(freeAt(x, y, CHWIDTH-1, ch)){return false;}
            else{return true;}
        }else{
            if(freeAt(x, y, z, this)){return false;}
            else{return true;}
        }
     
    }
    bool Chunk::checkY(int x, int y, int z){
        if(y >= CHHEIGHT){
            return true;
        }else if(y < 0){
            return false;
        }else{
            if(freeAt(x, y, z, this)){return false;}
            else{return true;}
        }
    }
     
    Chunk* Chunk::getChunkAt(std::string index){
        if(index.compare("x+1")){
            return m_ChunkList[0];
        }
        else if(index.compare("x-1")){
            return m_ChunkList[2];
        }
        else if(index.compare("z+1")){
            return m_ChunkList[1];
        }
        else if(index.compare("z-1")){
            return m_ChunkList[3];
        }
    }
     
    void Chunk::setBlockAt(std::string block, int x, int y, int z)
    {
        m_map[x][y][z] = block;
    }
     
    bool Chunk::freeAt(int x, int y, int z, Chunk* ch){
        if((ch->m_map[x][y][z]).compare("") == 0){
            return true;
        }
        return false;
    }
    PS : dans la méthode isVisible(4 arguments) le code plante pour la fonction getX(). De plus cette méthode est juste pour les tests !
    J'espère que vous comprendrez mon code malgré le manque de commentaires.
    Si vous avez des question n'hésitez pas !

    Merci d'avance pour votre aide !

  2. #2
    Membre expérimenté Avatar de Rewpparo
    Homme Profil pro
    Amateur
    Inscrit en
    Décembre 2005
    Messages
    170
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Charente Maritime (Poitou Charente)

    Informations professionnelles :
    Activité : Amateur

    Informations forums :
    Inscription : Décembre 2005
    Messages : 170
    Par défaut
    Sans trop regarder le code, je pense que c'est le pointeur vers les chunk voisines qui sont invalides. Vérifies d'où ils viennent, qu'ils sont bien initialisés a 0 dans le constructeur, que tu les définis bien à une valeur correcte, et valides les (en vérifiant s'ils ne sont pas nuls) avant chaque appel.
    Si tu initialise bien tes pointeurs a 0 des leur création et que tu vérifies s'ils sont nul avant de les utiliser, tu évite les segfaults de ce style.

  3. #3
    Invité
    Invité(e)
    Par défaut
    @Rewpparo :
    Merci pour ton aide !
    En fait c'était au moment del'attribution des chunks voisin ou je m'étais vachement planté...
    Merci !

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Réponses: 2
    Dernier message: 26/12/2013, 09h19
  2. signal sigsegv segmentation fault
    Par plus1 dans le forum C
    Réponses: 11
    Dernier message: 11/11/2013, 22h35
  3. Réponses: 2
    Dernier message: 07/03/2010, 00h20
  4. Réponses: 0
    Dernier message: 10/01/2008, 23h28
  5. Réponses: 15
    Dernier message: 15/04/2007, 13h31

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