On Wed, 28 Jan 2009 15:14:28 +0100, (Bruno Causse):
la plupart (et notament curl_easy_setopt) reclament des char* c
La fonction c_str() renvoie un "char const*", pas un "char*". On ne peut donc pas l'utiliser directement.
Tu as une fonction censée être appelée depuis du code C, et pas vraiment compatible avec C++. Tu dois donc l'encapsuler. (En passant, vérifie si ça n'est pas déjà fait -- il existe peut-être une bibliothèque d'interfaçage de tes fonctions C avec le C++.)
La méthode canonique pour créer un "char*" est d'utiliser std::vector<char> :
Vérifie tout de même que tu n'as pas besoin d'un buffer plus grand. Par exemple, si ta fonction C s'attend à recevoir un buffer de 256 octets, tu peux écrire :
Si, dans la doc de la bibliothèque en question, il est écrit explicitement qu'en aucun cas, la fonction ne pourra modifier le contenu du buffer, l'usage de "char*" est une erreur -- la fonction aurait dû réclamer un "char const*" (mais peut-être que ça n'existe tout simplement pas en C ?)
Dans ce cas, il faut indiquer au compilo que le prototype est erroné :
On Wed, 28 Jan 2009 15:14:28 +0100, pasdespam@free.fr (Bruno Causse):
la plupart (et notament curl_easy_setopt) reclament des char* c
La fonction c_str() renvoie un "char const*", pas un "char*".
On ne peut donc pas l'utiliser directement.
Tu as une fonction censée être appelée depuis du code C, et pas
vraiment compatible avec C++. Tu dois donc l'encapsuler.
(En passant, vérifie si ça n'est pas déjà fait -- il existe peut-être
une bibliothèque d'interfaçage de tes fonctions C avec le C++.)
La méthode canonique pour créer un "char*" est d'utiliser
std::vector<char> :
Vérifie tout de même que tu n'as pas besoin d'un buffer plus grand.
Par exemple, si ta fonction C s'attend à recevoir un buffer de 256
octets, tu peux écrire :
Si, dans la doc de la bibliothèque en question, il est écrit
explicitement qu'en aucun cas, la fonction ne pourra modifier le
contenu du buffer, l'usage de "char*" est une erreur -- la fonction
aurait dû réclamer un "char const*" (mais peut-être que ça n'existe
tout simplement pas en C ?)
Dans ce cas, il faut indiquer au compilo que le prototype est erroné :
On Wed, 28 Jan 2009 15:14:28 +0100, (Bruno Causse):
la plupart (et notament curl_easy_setopt) reclament des char* c
La fonction c_str() renvoie un "char const*", pas un "char*". On ne peut donc pas l'utiliser directement.
Tu as une fonction censée être appelée depuis du code C, et pas vraiment compatible avec C++. Tu dois donc l'encapsuler. (En passant, vérifie si ça n'est pas déjà fait -- il existe peut-être une bibliothèque d'interfaçage de tes fonctions C avec le C++.)
La méthode canonique pour créer un "char*" est d'utiliser std::vector<char> :
Vérifie tout de même que tu n'as pas besoin d'un buffer plus grand. Par exemple, si ta fonction C s'attend à recevoir un buffer de 256 octets, tu peux écrire :
Si, dans la doc de la bibliothèque en question, il est écrit explicitement qu'en aucun cas, la fonction ne pourra modifier le contenu du buffer, l'usage de "char*" est une erreur -- la fonction aurait dû réclamer un "char const*" (mais peut-être que ça n'existe tout simplement pas en C ?)
Dans ce cas, il faut indiquer au compilo que le prototype est erroné :
> bonjour, > > je tente d'utiliser CURL. > > la plupart (et notament curl_easy_setopt) reclament des char* c > (terminés par ) en parametre (des chaines a la mode c) > > si je fais (adresse en dur) > > curl_easy_setop (curl, CURLOPT_URL, > "http://monadresse:80/?action=PING"); > > c'est ok > > mais si je passe par un osstringstream url pour construire l'adresse, > puis > > url.str().c_str() en parametre j'ai une ereur a l'execution? > > <url> mailformed
Probablement parce que l'url est malformé. Mais comme tu ne produit aucun code à tester, on ne peut rien dire... En tout cas, chez moi ça marche:
non, mon adresse est correcte.
la soluce m'a ete fournie par fabien
avec une nouvelle decouverte :-)
std::vector < char> ( url.str().begin(), url.str().end()); ne fonctionne pas (2 chaines?)
mais
const std::string& sURL = url.str(); std::vector < char> ( sURL.begin(), sURL.end()); c'est ok
merci a tous
Pascal J. Bourguignon <pjb@informatimago.com> wrote:
pasdespam@free.fr (Bruno Causse) writes:
> bonjour,
>
> je tente d'utiliser CURL.
>
> la plupart (et notament curl_easy_setopt) reclament des char* c
> (terminés par ) en parametre (des chaines a la mode c)
>
> si je fais (adresse en dur)
>
> curl_easy_setop (curl, CURLOPT_URL,
> "http://monadresse:80/?action=PING");
>
> c'est ok
>
> mais si je passe par un osstringstream url pour construire l'adresse,
> puis
>
> url.str().c_str() en parametre j'ai une ereur a l'execution?
>
> <url> mailformed
Probablement parce que l'url est malformé. Mais comme tu ne produit
aucun code à tester, on ne peut rien dire... En tout cas, chez moi ça
marche:
non, mon adresse est correcte.
la soluce m'a ete fournie par fabien
avec une nouvelle decouverte :-)
std::vector < char> ( url.str().begin(), url.str().end());
ne fonctionne pas (2 chaines?)
mais
const std::string& sURL = url.str();
std::vector < char> ( sURL.begin(), sURL.end());
c'est ok
> bonjour, > > je tente d'utiliser CURL. > > la plupart (et notament curl_easy_setopt) reclament des char* c > (terminés par ) en parametre (des chaines a la mode c) > > si je fais (adresse en dur) > > curl_easy_setop (curl, CURLOPT_URL, > "http://monadresse:80/?action=PING"); > > c'est ok > > mais si je passe par un osstringstream url pour construire l'adresse, > puis > > url.str().c_str() en parametre j'ai une ereur a l'execution? > > <url> mailformed
Probablement parce que l'url est malformé. Mais comme tu ne produit aucun code à tester, on ne peut rien dire... En tout cas, chez moi ça marche:
non, mon adresse est correcte.
la soluce m'a ete fournie par fabien
avec une nouvelle decouverte :-)
std::vector < char> ( url.str().begin(), url.str().end()); ne fonctionne pas (2 chaines?)
mais
const std::string& sURL = url.str(); std::vector < char> ( sURL.begin(), sURL.end()); c'est ok
merci a tous
Fabien LE LEZ
On Wed, 28 Jan 2009 16:29:16 +0100, (Bruno Causse):
Ça n'a rien à voir avec le code que je t'ai indiqué.
je n'ai rien dit de tel.
James Kanze
On Jan 28, 3:35 pm, Fabien LE LEZ wrote:
On Wed, 28 Jan 2009 15:14:28 +0100, (Bruno Causse):
>la plupart (et notament curl_easy_setopt) reclament des char* c
La fonction c_str() renvoie un "char const*", pas un "char*". On ne peut donc pas l'utiliser directement.
Tu as une fonction censée être appelée depuis du code C, et pas vraiment compatible avec C++. Tu dois donc l'encapsuler. (En passant, vérifie si ça n'est pas déjà fait -- il existe peut- être une bibliothèque d'interfaçage de tes fonctions C avec le C++.)
La méthode canonique pour créer un "char*" est d'utiliser std::vector<char> :
Pas vraiment. Ça dépend de l'utilisation du char* dans la fonction. Beaucoup de fonctions C ne sont pas « const correct » ; elle prend un char* sans modifier la chaîne. Dans ce cas-là, la méthode canonique, c'est un const_cast sur le resultat d'un appel à string::c_str().
Du fait que ça marche quand il passe une chaîne constante, j'imagine que c'est le cas ici. Le vector<char> n'est nécessaire que dans le cas où la fonction veut modifier (c-à-d qu'on passe un buffer, plutôt qu'une chaîne).
[...[
Si, dans la doc de la bibliothèque en question, il est écrit explicitement qu'en aucun cas, la fonction ne pourra modifier le contenu du buffer, l'usage de "char*" est une erreur -- la fonction aurait dû réclamer un "char const*" (mais peut-être que ça n'existe tout simplement pas en C ?)
Ça existe, mais son utilisation n'est pas aussi répandue qu'en C++. Si certaines bibliothèques (la bibliothèque standard du langage, Posix, etc.) s'appliquent à l'utiliser de façon systèmatique, d'autres l'ignore complètement.
-- James Kanze (GABI Software) email: Conseils en informatique orientée objet/ Beratung in objektorientierter Datenverarbeitung 9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34
On Jan 28, 3:35 pm, Fabien LE LEZ <grams...@gramster.com> wrote:
On Wed, 28 Jan 2009 15:14:28 +0100, pasdes...@free.fr (Bruno Causse):
>la plupart (et notament curl_easy_setopt) reclament des char* c
La fonction c_str() renvoie un "char const*", pas un "char*".
On ne peut donc pas l'utiliser directement.
Tu as une fonction censée être appelée depuis du code C, et pas
vraiment compatible avec C++. Tu dois donc l'encapsuler.
(En passant, vérifie si ça n'est pas déjà fait -- il existe peut- être
une bibliothèque d'interfaçage de tes fonctions C avec le C++.)
La méthode canonique pour créer un "char*" est d'utiliser
std::vector<char> :
Pas vraiment. Ça dépend de l'utilisation du char* dans la
fonction. Beaucoup de fonctions C ne sont pas « const
correct » ; elle prend un char* sans modifier la chaîne. Dans
ce cas-là, la méthode canonique, c'est un const_cast sur le
resultat d'un appel à string::c_str().
Du fait que ça marche quand il passe une chaîne constante,
j'imagine que c'est le cas ici. Le vector<char> n'est nécessaire
que dans le cas où la fonction veut modifier (c-à-d qu'on passe
un buffer, plutôt qu'une chaîne).
[...[
Si, dans la doc de la bibliothèque en question, il est écrit
explicitement qu'en aucun cas, la fonction ne pourra modifier
le contenu du buffer, l'usage de "char*" est une erreur -- la
fonction aurait dû réclamer un "char const*" (mais peut-être
que ça n'existe tout simplement pas en C ?)
Ça existe, mais son utilisation n'est pas aussi répandue qu'en
C++. Si certaines bibliothèques (la bibliothèque standard du
langage, Posix, etc.) s'appliquent à l'utiliser de façon
systèmatique, d'autres l'ignore complètement.
--
James Kanze (GABI Software) email:james.kanze@gmail.com
Conseils en informatique orientée objet/
Beratung in objektorientierter Datenverarbeitung
9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34
On Wed, 28 Jan 2009 15:14:28 +0100, (Bruno Causse):
>la plupart (et notament curl_easy_setopt) reclament des char* c
La fonction c_str() renvoie un "char const*", pas un "char*". On ne peut donc pas l'utiliser directement.
Tu as une fonction censée être appelée depuis du code C, et pas vraiment compatible avec C++. Tu dois donc l'encapsuler. (En passant, vérifie si ça n'est pas déjà fait -- il existe peut- être une bibliothèque d'interfaçage de tes fonctions C avec le C++.)
La méthode canonique pour créer un "char*" est d'utiliser std::vector<char> :
Pas vraiment. Ça dépend de l'utilisation du char* dans la fonction. Beaucoup de fonctions C ne sont pas « const correct » ; elle prend un char* sans modifier la chaîne. Dans ce cas-là, la méthode canonique, c'est un const_cast sur le resultat d'un appel à string::c_str().
Du fait que ça marche quand il passe une chaîne constante, j'imagine que c'est le cas ici. Le vector<char> n'est nécessaire que dans le cas où la fonction veut modifier (c-à-d qu'on passe un buffer, plutôt qu'une chaîne).
[...[
Si, dans la doc de la bibliothèque en question, il est écrit explicitement qu'en aucun cas, la fonction ne pourra modifier le contenu du buffer, l'usage de "char*" est une erreur -- la fonction aurait dû réclamer un "char const*" (mais peut-être que ça n'existe tout simplement pas en C ?)
Ça existe, mais son utilisation n'est pas aussi répandue qu'en C++. Si certaines bibliothèques (la bibliothèque standard du langage, Posix, etc.) s'appliquent à l'utiliser de façon systèmatique, d'autres l'ignore complètement.
-- James Kanze (GABI Software) email: Conseils en informatique orientée objet/ Beratung in objektorientierter Datenverarbeitung 9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34
James Kanze
On Jan 28, 4:29 pm, (Bruno Causse) wrote:
Pascal J. Bourguignon wrote:
> (Bruno Causse) writes:
> > je tente d'utiliser CURL.
> > la plupart (et notament curl_easy_setopt) reclament des > > char* c (terminés par ) en parametre (des chaines a la > > mode c)
> > mais si je passe par un osstringstream url pour construire > > l'adresse, puis
> > url.str().c_str() en parametre j'ai une ereur a l'execution?
> > <url> mailformed
> Probablement parce que l'url est malformé. Mais comme tu ne > produit aucun code à tester, on ne peut rien dire... En > tout cas, chez moi ça marche:
non, mon adresse est correcte.
la soluce m'a ete fournie par fabien
avec une nouvelle decouverte :-)
std::vector < char> ( url.str().begin(), url.str().end()); ne fonctionne pas (2 chaines?)
Tout à fait.
mais
const std::string& sURL = url.str();
Pourquoi la référence ici ?
std::vector < char> ( sURL.begin(), sURL.end()); c'est ok
Il serait quand même intéressant de voir ton code d'origine. A priori, je taperais sur un problème de durée de vie d'un temporaire quelque part. Si tu appelles directement :
std::ostringstream s ; // ... someFunction( s.str().c_str() ) ;
ça doit marcher. (J'en fait autant assez souvent, sans problèmes.) En revanche, la chaîne renvoyée par s.str() est bien un temporaire (une copie de la chaîne dans le stream), dont la durée de vie termine à la fin de l'expression complète qui le contient. Je ne crois pas trop à ce que le vector soit nécessaire en soit, mais c'est une variable, avec une durée de vie plus longue qu'un temporaire, et ça peut faire une différence importante.
-- James Kanze (GABI Software) email: Conseils en informatique orientée objet/ Beratung in objektorientierter Datenverarbeitung 9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34
On Jan 28, 4:29 pm, pasdes...@free.fr (Bruno Causse) wrote:
Pascal J. Bourguignon <p...@informatimago.com> wrote:
> pasdes...@free.fr (Bruno Causse) writes:
> > je tente d'utiliser CURL.
> > la plupart (et notament curl_easy_setopt) reclament des
> > char* c (terminés par ) en parametre (des chaines a la
> > mode c)
> > mais si je passe par un osstringstream url pour construire
> > l'adresse, puis
> > url.str().c_str() en parametre j'ai une ereur a l'execution?
> > <url> mailformed
> Probablement parce que l'url est malformé. Mais comme tu ne
> produit aucun code à tester, on ne peut rien dire... En
> tout cas, chez moi ça marche:
non, mon adresse est correcte.
la soluce m'a ete fournie par fabien
avec une nouvelle decouverte :-)
std::vector < char> ( url.str().begin(), url.str().end());
ne fonctionne pas (2 chaines?)
Tout à fait.
mais
const std::string& sURL = url.str();
Pourquoi la référence ici ?
std::vector < char> ( sURL.begin(), sURL.end());
c'est ok
Il serait quand même intéressant de voir ton code d'origine. A
priori, je taperais sur un problème de durée de vie d'un
temporaire quelque part. Si tu appelles directement :
std::ostringstream s ;
// ...
someFunction( s.str().c_str() ) ;
ça doit marcher. (J'en fait autant assez souvent, sans
problèmes.) En revanche, la chaîne renvoyée par s.str() est bien
un temporaire (une copie de la chaîne dans le stream), dont la
durée de vie termine à la fin de l'expression complète qui le
contient. Je ne crois pas trop à ce que le vector soit
nécessaire en soit, mais c'est une variable, avec une durée de
vie plus longue qu'un temporaire, et ça peut faire une
différence importante.
--
James Kanze (GABI Software) email:james.kanze@gmail.com
Conseils en informatique orientée objet/
Beratung in objektorientierter Datenverarbeitung
9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34
> > mais si je passe par un osstringstream url pour construire > > l'adresse, puis
> > url.str().c_str() en parametre j'ai une ereur a l'execution?
> > <url> mailformed
> Probablement parce que l'url est malformé. Mais comme tu ne > produit aucun code à tester, on ne peut rien dire... En > tout cas, chez moi ça marche:
non, mon adresse est correcte.
la soluce m'a ete fournie par fabien
avec une nouvelle decouverte :-)
std::vector < char> ( url.str().begin(), url.str().end()); ne fonctionne pas (2 chaines?)
Tout à fait.
mais
const std::string& sURL = url.str();
Pourquoi la référence ici ?
std::vector < char> ( sURL.begin(), sURL.end()); c'est ok
Il serait quand même intéressant de voir ton code d'origine. A priori, je taperais sur un problème de durée de vie d'un temporaire quelque part. Si tu appelles directement :
std::ostringstream s ; // ... someFunction( s.str().c_str() ) ;
ça doit marcher. (J'en fait autant assez souvent, sans problèmes.) En revanche, la chaîne renvoyée par s.str() est bien un temporaire (une copie de la chaîne dans le stream), dont la durée de vie termine à la fin de l'expression complète qui le contient. Je ne crois pas trop à ce que le vector soit nécessaire en soit, mais c'est une variable, avec une durée de vie plus longue qu'un temporaire, et ça peut faire une différence importante.
-- James Kanze (GABI Software) email: Conseils en informatique orientée objet/ Beratung in objektorientierter Datenverarbeitung 9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34
Fabien LE LEZ
On Thu, 29 Jan 2009 00:11:13 -0800 (PST), James Kanze :
Beaucoup de fonctions C ne sont pas « const correct » ; elle prend un char* sans modifier la chaîne.
Yep, c'est bien ce que je dis plus bas :
Si, dans la doc de la bibliothèque en question, il est écrit explicitement qu'en aucun cas, la fonction ne pourra modifier le contenu du buffer, l'usage de "char*" est une erreur -- la fonction aurait dû réclamer un "char const*"
Faut bien lire la doc. Par exemple, la fonction CreateProcess de l'API Win32 est tordue : on passe la ligne de commande sous forme d'une chaîne constante... sauf si on compile en Unicode.
"The Unicode version of this function, CreateProcessW, can modify the contents of this string. Therefore, this parameter cannot be a pointer to read-only memory (such as a const variable or a literal string). If this parameter is a constant string, the function may cause an access violation." http://msdn.microsoft.com/en-us/library/ms682425.aspx
On Thu, 29 Jan 2009 00:11:13 -0800 (PST), James Kanze
<james.kanze@gmail.com>:
Beaucoup de fonctions C ne sont pas « const
correct » ; elle prend un char* sans modifier la chaîne.
Yep, c'est bien ce que je dis plus bas :
Si, dans la doc de la bibliothèque en question, il est écrit
explicitement qu'en aucun cas, la fonction ne pourra modifier
le contenu du buffer, l'usage de "char*" est une erreur -- la
fonction aurait dû réclamer un "char const*"
Faut bien lire la doc. Par exemple, la fonction CreateProcess de
l'API Win32 est tordue : on passe la ligne de commande sous forme
d'une chaîne constante... sauf si on compile en Unicode.
"The Unicode version of this function, CreateProcessW, can modify the
contents of this string. Therefore, this parameter cannot be a pointer
to read-only memory (such as a const variable or a literal string). If
this parameter is a constant string, the function may cause an access
violation."
http://msdn.microsoft.com/en-us/library/ms682425.aspx
On Thu, 29 Jan 2009 00:11:13 -0800 (PST), James Kanze :
Beaucoup de fonctions C ne sont pas « const correct » ; elle prend un char* sans modifier la chaîne.
Yep, c'est bien ce que je dis plus bas :
Si, dans la doc de la bibliothèque en question, il est écrit explicitement qu'en aucun cas, la fonction ne pourra modifier le contenu du buffer, l'usage de "char*" est une erreur -- la fonction aurait dû réclamer un "char const*"
Faut bien lire la doc. Par exemple, la fonction CreateProcess de l'API Win32 est tordue : on passe la ligne de commande sous forme d'une chaîne constante... sauf si on compile en Unicode.
"The Unicode version of this function, CreateProcessW, can modify the contents of this string. Therefore, this parameter cannot be a pointer to read-only memory (such as a const variable or a literal string). If this parameter is a constant string, the function may cause an access violation." http://msdn.microsoft.com/en-us/library/ms682425.aspx