Bonjour,
Est-il possible d'envoyer une structure depuis le processus père vers le fils par l'intermedière d'un pipe?
Bonjour,
Est-il possible d'envoyer une structure depuis le processus père vers le fils par l'intermedière d'un pipe?
Si elle est 'droite', oui (pas de pointeurs). Je préfère cependant un format texte, c'est plus sûr.Envoyé par Vodlich
Merci pour ta réponse,
Arf.. ca m'arrange pas tout ça !
Voici ma structure a communiquer(COMM) :
J'arrive quand même à communiquer la partie MESSAGE de la structure COMM, mais pile, pas moyen(pas 'droite').
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 typedef struct { /* structure pour stocker les */ int x; /* coordonnees dans la matrice jeu */ int y; } coord; typedef struct pile /*pour stocker les coordonnees*/ { coord valeur; struct pile *prec; } pile ; typedef enum /*pour traiter les messages*/ { LISTE_COMM, ERREUR, ERREUR_ROBOT, ERREUR_MURS, ERREUR_ENERGIE, MURS, ROBOT, ENERGIE } MESSAGE; typedef struct { /* structure pour stocker le */ MESSAGE m; /* type de message et les coordonnees */ pile *p; } COMM;
Ya t-il un autre moyen pour communiquer cette structure?
Sinon, j'ai un autre problème avec le pipe, quand le père envoie du texte avec un espace, le fils le recois en deux textes coupé au niveau de l'espace et non un bloc texte unique. Comment y remédier ?
Personne pour m'aider ?![]()
Soit tu fais un bloc binaire 'droit' (tu linéarises au format format "longueur, donnees", par exemple soit tu convertis en texte. On a pas déjà dit ça ?Envoyé par Vodlich
J'ai opté pour la convertion en chaine de caractère (ne sachant pas ce qu'est "un bloc binaire 'droit' (tu linéarises au format format "longueur, donnees")", si c'est possible d'avoir plus d'explication pour infos, je prends!)
Voici le code ma fonction de conversion, j'aimerais avoir l'avis de quelqu'un dessus sachant que la fonction fonctionne mais que je ne maitrise pas les pointeurs et chaines parfaitement.
et le programme de test
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 char *convertion_COMM_chaine(COMM mess) { char *temp=malloc(8*longueur_pile(mess.p)*sizeof(char)+3*sizeof(char)); /* reserve exactement l'espace necessaire pour stocker mess 8 car la chaine finale prend 8 caracteres au maximum pour un maillon de la pile et 3 pour stocker mess.m et '\0' */ /* attention, ne marche que pour des coordonnées <100 et >=0*/ char *entier=malloc(3*sizeof(char)); coord c; switch(mess.m) { case LISTE : strcpy(temp,"0_"); break; case ERREUR : strcpy(temp,"1_"); break; case ERREUR_MURS : strcpy(temp,"2_"); break; case ERREUR_ENERGIE : strcpy(temp,"3_"); break; case ERREUR_ROBOT : strcpy(temp,"4_"); break; case MURS : strcpy(temp,"5_"); break; case ENERGIE : strcpy(temp,"6_"); break; case ROBOT : strcpy(temp,"7_"); break; default: break; } while(mess.p!=NULL) { c.x=mess.p->valeur.x; c.y=mess.p->valeur.y; sprintf(entier,"(%d,%d)_",c.x,c.y); strcat(temp,entier); depiler(&mess.p); } return temp; }
PS : les structures sont celles données dans un post plus haut.
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 int main(void) { char *ch; COMM mess; coord V1; coord V2; coord V3; V1.x=10; V1.y=12; V2.x=4; V2.y=61; V3.x=1; V3.y=20; mess.m=ROBOT; mess.p=NULL; empiler(&mess.p,V1); empiler(&mess.p,V2); empiler(&mess.p,V3); //afficher_pile(mess.p); printf("\n%s\n",convertion_COMM_chaine(mess)); return 0; }
Merci d'avance.
"conversion"Envoyé par Vodlich
Tu définis un format pour les longueurs (par exemple 2 bytes) codés 'réseau', c'est à dire MSB en tête)sachant pas ce qu'est "un bloc binaire 'droit' (tu linéarises au format format "longueur, donnees")", si c'est possible d'avoir plus d'explication pour infos, je prends!)
Ensuite, tu places tes données de longueur variable dans un tableau bytes.
Par exemple
devient
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2 char *pa="Hello"; char *pb="world";
je te laisse ecrire le code de conversion. Nota. On trouve en général htons() et ntohs() pour les conversions machine <-> réseau. Sinon
Code : Sélectionner tout - Visualiser dans une fenêtre à part unsigned char data [] = {0,5,'h','e','l','l','o', 0,5,'w','o','r','l','d'};
http://emmanuel-delahaye.developpez.com/clib.htm
Module HTON. Attention, ça dépend de la machine.
Le principe a l'air correct, mais ce code est incomplet. Il ne compile pas, il n'est pas pas testable.Voici le code ma fonction de conversion, j'aimerais avoir l'avis de
Envoyé par Emmanuel Delahaye
![]()
Merci pour tes explications mais je vais quand même rester sur ma méthode.
J'ai oublié de mettre les fonctions pour la pile.Voici le code complet :
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
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184 #include <stdio.h> #include<string.h> #include <stdlib.h> typedef struct { /* structure pour stocker les */ int x; /* coordonnees dans la matrice jeu */ int y; } coord; typedef struct pile /*pour stocker les coordonnees*/ { coord valeur; struct pile *prec; } pile ; typedef enum /*pour traiter les messages*/ { LISTE, ERREUR, ERREUR_ROBOT, ERREUR_MURS, ERREUR_ENERGIE, MURS, ROBOT, ENERGIE } MESSAGE; typedef struct { /* structure pour stocker les */ MESSAGE m; /* le type de message et les coordonnees */ pile *p; } COMM; /*-------------------------------------------------------------------*/ /* Fonctions de gestion d'une pile */ void empiler(pile **p, coord Val) { pile *element = malloc(sizeof(pile)); if(!element) return; element->valeur = Val; element->prec = *p; *p = element; } void depiler(pile **p) { coord Val; pile *tmp; if(!*p) exit(1); tmp = (*p)->prec; Val = (*p)->valeur; free(*p); *p = tmp; } void raz(pile **p) { pile *tmp; while(*p) { tmp = (*p)->prec; free(*p); *p = tmp; } } void afficher_pile(pile *p) { while(p) { printf("(%d,%d) ",p->valeur.x,p->valeur.y); p = p->prec; } } int longueur_pile(pile *p) { int n=0; while(p) { n++; p = p->prec; } return n; } /*-------------------------------------------------------------------*/ char *conversion_COMM_chaine(COMM mess) { char *temp=malloc(8*longueur_pile(mess.p)*sizeof(char)+3*sizeof(char)); /* reserve exactement l'espace necessaire pour stocker mess 8 car la chaine finale prend 8 caracteres au maximum pour un maillon de la pile et 3 pour stocker mess.m et '\0' */ /* attention, ne marche que pour des coordonnées <100 et >=0 */ char *entier=malloc(3*sizeof(char)); coord c; switch(mess.m) { case LISTE : strcpy(temp,"0_"); break; case ERREUR : strcpy(temp,"1_"); break; case ERREUR_MURS : strcpy(temp,"2_"); break; case ERREUR_ENERGIE : strcpy(temp,"3_"); break; case ERREUR_ROBOT : strcpy(temp,"4_"); break; case MURS : strcpy(temp,"5_"); break; case ENERGIE : strcpy(temp,"6_"); break; case ROBOT : strcpy(temp,"7_"); break; default: break; } while(mess.p!=NULL) { c.x=mess.p->valeur.x; c.y=mess.p->valeur.y; sprintf(entier,"(%d,%d)_",c.x,c.y); strcat(temp,entier); depiler(&mess.p); } return temp; } int main(void) { char *ch; COMM mess; coord V1; coord V2; coord V3; V1.x=10; V1.y=12; V2.x=4; V2.y=61; V3.x=1; V3.y=20; mess.m=ROBOT; mess.p=NULL; empiler(&mess.p,V1); empiler(&mess.p,V2); empiler(&mess.p,V3); afficher_pile(mess.p); printf("\n%s\n",conversion_COMM_chaine(mess)); raz(&mess.p); return 0; }
Un petit coup de detecteur de mensonges...Envoyé par Vodlich
Visiblement, il y a un petit problème de libération des ressources...
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6 SYSALLOC Bloc 003D2510 freed at line 65 of 'main.c' not allocated SYSALLOC Bloc 003D24F8 freed at line 65 of 'main.c' not allocated SYSALLOC Bloc 003D24E0 freed at line 65 of 'main.c' not allocated SYSALLOC Bloc 003D2528 (27 bytes) malloc'ed at line 95 of 'main.c' not freed SYSALLOC Bloc 003D2470 (3 bytes) malloc'ed at line 101 of 'main.c' not freed
Simplification (inutile d'allouer un tableau de taille fixe), instrumentation du code :
Ca donne :
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
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207 #include "ed/inc/sys.h" #include <stdio.h> #include<string.h> #include <stdlib.h> typedef struct { /* structure pour stocker les */ int x; /* coordonnees dans la matrice jeu */ int y; } coord; typedef struct pile /*pour stocker les coordonnees*/ { coord valeur; struct pile *prec; } pile ; typedef enum /*pour traiter les messages*/ { LISTE, ERREUR, ERREUR_ROBOT, ERREUR_MURS, ERREUR_ENERGIE, MURS, ROBOT, ENERGIE } MESSAGE; typedef struct { /* structure pour stocker les */ MESSAGE m; /* le type de message et les coordonnees */ pile *p; } COMM; /*-------------------------------------------------------------------*/ /* Fonctions de gestion d'une pile */ void empiler(pile **p, coord Val) { pile *element = malloc(sizeof(pile)); if(!element) return; element->valeur = Val; element->prec = *p; *p = element; } void depiler(pile **p) { coord Val; pile *tmp; if(!*p) exit(1); tmp = (*p)->prec; Val = (*p)->valeur; free(*p); *p = tmp; } void raz(pile **p) { pile *tmp; while(*p) { tmp = (*p)->prec; free(*p); *p = tmp; } } void afficher_pile(pile *p) { while(p) { printf("(%d,%d) ",p->valeur.x,p->valeur.y); p = p->prec; } } int longueur_pile(pile *p) { int n=0; while(p) { n++; p = p->prec; } return n; } /*-------------------------------------------------------------------*/ char *conversion_COMM_chaine(COMM mess) { size_t size_temp = 8 * longueur_pile (mess.p) + 3; char *temp = malloc (size_temp); if (temp != NULL) { LIM_PTR(temp, size_temp); /* reserve exactement l'espace necessaire pour stocker mess 8 car la chaine finale prend 8 caracteres au maximum pour un maillon de la pile et 3 pour stocker mess.m et '\0' */ /* attention, ne marche que pour des coordonnées <100 et >=0 */ coord c; switch(mess.m) { case LISTE : strcpy(temp,"0_"); break; case ERREUR : strcpy(temp,"1_"); break; case ERREUR_MURS : strcpy(temp,"2_"); break; case ERREUR_ENERGIE : strcpy(temp,"3_"); break; case ERREUR_ROBOT : strcpy(temp,"4_"); break; case MURS : strcpy(temp,"5_"); break; case ENERGIE : strcpy(temp,"6_"); break; case ROBOT : strcpy(temp,"7_"); break; default: break; } while(mess.p!=NULL) { char entier[3]; LIM_STR(entier); c.x=mess.p->valeur.x; c.y=mess.p->valeur.y; sprintf(entier,"(%d,%d)_",c.x,c.y); CHK_STR(entier); strcat(temp,entier); CHK_PTR(temp,size_temp ); depiler(&mess.p); } } return temp; } int main(void) { char *ch; COMM mess; coord V1; coord V2; coord V3; V1.x=10; V1.y=12; V2.x=4; V2.y=61; V3.x=1; V3.y=20; mess.m=ROBOT; mess.p=NULL; empiler(&mess.p,V1); empiler(&mess.p,V2); empiler(&mess.p,V3); afficher_pile(mess.p); printf("\n%s\n",conversion_COMM_chaine(mess)); raz(&mess.p); return 0; }
Ca signifie en clair que le tableau de 3 char est trop petit...
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11 (1,20) (4,61) (10,12) SYS: assertion '(entier)[sizeof (entier) - 1]==0' failed a t main.c:161 SYS: SYS_print_stack() : Undefined in ISO-C SYS: *** EXIT *** SYSALLOC min=4294967295 max=4294967295 delta=0 SYSALLOC Err: Not-matched list: SYSALLOC Bloc 003D24E0 (12 bytes) malloc'ed at line 45 of 'main.c' not freed SYSALLOC Bloc 003D24F8 (12 bytes) malloc'ed at line 45 of 'main.c' not freed SYSALLOC Bloc 003D2510 (12 bytes) malloc'ed at line 45 of 'main.c' not freed SYSALLOC Bloc 003D2528 (27 bytes) malloc'ed at line 102 of 'main.c' not freed
On s'en serait un peu douté...
Le code manquant est là :
http://emmanuel-delahaye.developpez.com/clib.htm
Je ne comprend pas ce que tout ça veut dire.:
Tu parles de quoi ? Bouton [Citer] please...Envoyé par Vodlich
Deja, si je comprend bien, ce codeest équivalent à :
Code : Sélectionner tout - Visualiser dans une fenêtre à part LIM_PTR(temp, size_temp);.
Code : Sélectionner tout - Visualiser dans une fenêtre à part (temp)[(size_temp) -1]=0;
Si c'est bien ça, je ne comprend pas ce qu'il fait. Idem pour
Code : Sélectionner tout - Visualiser dans une fenêtre à part LIM_STR(entier);
Code : Sélectionner tout - Visualiser dans une fenêtre à part CHK_STR(entier);Sinon, si je modifie la déclaration de entier comme ceci :
Code : Sélectionner tout - Visualiser dans une fenêtre à part CHK_PTR(temp,size_temp );
c'est pas suffisant ?
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 char *conversion_COMM_chaine(COMM mess) { char *temp=malloc(8*longueur_pile(mess.p)*sizeof(char)+3*sizeof(char)); /* reserve exactement l'espace necessaire pour stocker mess 8 car la chaine finale prend 8 caracteres au maximum pour un maillon de la pile et 3 pour stocker mess.m et '\0' */ /* attention, ne marche que pour des coordonnées <100 et >=0 */ char entier[9]; coord c; switch(mess.m) { case LISTE : strcpy(temp,"0_"); break; case ERREUR : strcpy(temp,"1_"); break; case ERREUR_MURS : strcpy(temp,"2_"); break; case ERREUR_ENERGIE : strcpy(temp,"3_"); break; case ERREUR_ROBOT : strcpy(temp,"4_"); break; case MURS : strcpy(temp,"5_"); break; case ENERGIE : strcpy(temp,"6_"); break; case ROBOT : strcpy(temp,"7_"); break; default: break; } while(mess.p!=NULL) { c.x=mess.p->valeur.x; c.y=mess.p->valeur.y; sprintf(entier,"(%d,%d)_",c.x,c.y); strcat(temp,entier); depiler(&mess.p); } return temp; }
Attention, malloc() peut échouer. J'avais ajouté un test. Je perd mon temps ou quoi ?Envoyé par Vodlich
Il n'est pas pratique de définir une variable loin de son utilisation... Il suffit qu'elle soit en tête de bloc...
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2 char entier[9];
En tout cas, chez moi, ça ne casse plus. iL reste encore des problèmes de libération de la mémoire...c'est pas suffisant ?
Certaines adresses sont libérées 2 fois, d'autres pas du tout...
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8 (1,20) (4,61) (10,12) 7_(1,20)_(4,61)_(10,12)_ SYSALLOC Err: Not-matched list: SYSALLOC Bloc 003D2510 freed at line 71 of 'main.c' not allocated SYSALLOC Bloc 003D24F8 freed at line 71 of 'main.c' not allocated SYSALLOC Bloc 003D24E0 freed at line 71 of 'main.c' not allocated SYSALLOC Bloc 003D2528 (27 bytes) malloc'ed at line 102 of 'main.c' not freed
J'ai ajouté le test sur le malloc(), désolé.
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 char *conversion_COMM_chaine(COMM mess) { char *temp=malloc(8*longueur_pile(mess.p)*sizeof(char)+3*sizeof(char)); /* reserve exactement l'espace necessaire pour stocker mess 8 car la chaine finale prend 8 caracteres au maximum pour un maillon de la pile et 3 pour stocker mess.m et '\0' */ /* attention, ne marche que pour des coordonnées <100 et >=0 */ if(temp!=NULL) { switch(mess.m) { case LISTE : strcpy(temp,"0_"); break; case ERREUR : strcpy(temp,"1_"); break; case ERREUR_MURS : strcpy(temp,"2_"); break; case ERREUR_ENERGIE : strcpy(temp,"3_"); break; case ERREUR_ROBOT : strcpy(temp,"4_"); break; case MURS : strcpy(temp,"5_"); break; case ROBOT : strcpy(temp,"6_"); break; case ENERGIE : strcpy(temp,"7_"); break; default: break; } while(mess.p!=NULL) { char entier[9]; coord c; c.x=mess.p->valeur.x; c.y=mess.p->valeur.y; sprintf(entier,"(%d,%d)_",c.x,c.y); strcat(temp,entier); depiler(&mess.p); } raz(&mess.p); } return temp; }Je pense que tout est libéré.
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 int main(void) { char *ch; COMM mess; coord V1; coord V2; coord V3; V1.x=10; V1.y=12; V2.x=4; V2.y=61; V3.x=1; V3.y=20; mess.m=ERREUR; mess.p=NULL; empiler(&mess.p,V1); empiler(&mess.p,V2); empiler(&mess.p,V3); afficher_pile(mess.p); ch=conversion_COMM_chaine(mess); printf("\n%s\n",ch); free(ch); return 0; }
C'est OK.Envoyé par Vodlich
Attention, comme conversion_COMM_chaine() peut retourner NULL :
Et aussi, prendre l'habitude de forcer le pointeur à NULL une fois libéré. Ca facilite la mise au point...
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7 ch = conversion_COMM_chaine (mess); if (ch != NULL) { printf ("\n%s\n",ch); free (ch); }
Je passe sur les conventions de nommage...
Code : Sélectionner tout - Visualiser dans une fenêtre à part free (ch), ch = NULL;
http://emmanuel-delahaye.developpez.com/codage.htm
C'est nickel tout ça![]()
Un grand merci à toi Emmanuel Delahaye pour m'avoir consacré de ton temps.
A+ sur le forum.
Partager