Twitter iPhone pliant OnePlus 11 PS5 Disney+ Orange Livebox Windows 11

PHP et Sybase

9 réponses
Avatar
David
Bonjour,
je suis débutant dans ce monde, alors pardonnez mes erreurs possibles.

Je rencontre un problème sur mon site avec la version 4.3.9 ou
5.0.2 de PHP en utilisant Sybase.
Voici ma configuration actuelle :
hpux 11.0, Sybase 12.0, PHP 4.3.8

Mes pages sont assez simples (je suis débutant en PHP et programmation
web). Elles se contentent principalement d'un select en base
et d'un affichage par un while sur le résultat, quelques include
pour des fonctions générales mais rien de plus.
Avec PHP 4.3.8 tout va pour le mieux.

J'ai essayé dernièrement de passer à la version 4.3.9 (j'ai les
mêmes problèmes avec PHP 5.0.2) en compilant de la même façon
que la 4.3.8. Mais à l'utilisation, le process php core, et
mon serveur Apache m'indique le fin anormal de mon processus,
dans mes pages PHP, j'obtiens des messages d'erreur comme si
ma connexion Sybase n'est plus active ( ressource n'est pas une
connexion valide ou message d'erreur de typage ??? )

Quelqu'un utilise t-il PHP avec Sybase et a eu ce genre de problème ?
Sinon quelles informations sont suceptibles d'être pertinentes
pour essayer de trouver d'où vient le problème ?

Merci de votre aide.

PS : Pour le moment, je suis donc resté à la version 4.3.8 mais
j'aimerai ne pas avoir à me passer de la version 5.

David.

9 réponses

Avatar
John GALLET
Bonjour,

je suis débutant dans ce monde, alors pardonnez mes erreurs possibles.
Là ça ressemble quand même à un problème "à la con"...


hpux 11.0, Sybase 12.0, PHP 4.3.8
Ok. Pas classique, mais connu quand même.


Mes pages sont assez simples (je suis débutant en PHP et programmation
web). Elles se contentent principalement d'un select en base
et d'un affichage par un while sur le résultat, quelques include
pour des fonctions générales mais rien de plus.
Avec PHP 4.3.8 tout va pour le mieux.
Ok.


J'ai essayé dernièrement de passer à la version 4.3.9 (j'ai les
mêmes problèmes avec PHP 5.0.2) en compilant de la même façon
que la 4.3.8.


On va pas passer au travers : il va nous falloit le détail de la manière
dont tu compiles.

Mais à l'utilisation, le process php core,


Un vrai coredump ? Un vrai de vrai ? Il est compilé en cgi alors ? pas
moyen de le prendre en dbx juste pour voir, ou au moins de faire un
strings dessus ?

mon serveur Apache m'indique le fin anormal de mon processus,
dans mes pages PHP, j'obtiens des messages d'erreur comme si
ma connexion Sybase n'est plus active ( ressource n'est pas une
connexion valide ou message d'erreur de typage ??? )
Il va aussi nous falloir le message EXACT et la portion de code

(php) approximative où ça se vautre.

Sinon quelles informations sont suceptibles d'être pertinentes
pour essayer de trouver d'où vient le problème ?
Les options de compil, ça c'est sûr. La liste des autres changements de la

config (mise à jour au passage de sybase ou de l'open client par exemple.

a++
JG

Avatar
David
Je ne vais pas pouvoir faire plus de test ce WE
mais j'ai quelques infos suplémentaires.

hpux 11.0, Sybase 12.0, PHP 4.3.8


Ok. Pas classique, mais connu quand même.


J'ai cru comprendre que ma configuration était assez rare.
Alors j'ai essayé de reproduire le problème ailleurs.
Et j'ai le même problème avec la configuration suivante :
Windows NT4, Apache 1.3.31, et PHP 4.3.9.

En installant tous les programmes à partir des versions pré-compilées
dispo sur les sites respectifs des applis. Donc pas de compilation de la
part.

Lors de l'exécution de mes scripts tout est ok en 4.3.8, et j'ai
un Dr Watson sur Apache en 4.3.9.

On va pas passer au travers : il va nous falloir le détail de la manière
dont tu compiles.


Ok, je posterai les CFLAGS, LDFLAGS et la ligne configure que j'utilise.
Mais rien de bien rare ( -fast, +DAportable, -s, puis un configure sans
MySQl, un support Sybase CT, et en module Apache 1.3.31 avec aspx )

Un vrai coredump ? Un vrai de vrai ? Il est compilé en cgi alors ? pas
moyen de le prendre en dbx juste pour voir, ou au moins de faire un
strings dessus ?


Oui, Oui, Non pas en CGI, en module libphp4.sl, ajouté au lancement
d'Apache par AddModule. J'ai pas osé le wdb... encore.

Il va aussi nous falloir le message EXACT et la portion de code
(php) approximative où ça se vautre.


Je vais poster un exemple minimal qui plante.

Les options de compil, ça c'est sûr. La liste des autres changements de la
config (mise à jour au passage de sybase ou de l'open client par exemple.


Ok, je poste ça lundi soir.


a++
JG


Merci de votre temps et bon WE.
David.


Avatar
David
J'ai finalement téléchargé la version de Sybase 12.5 pour linux.
Conclusion : même bug sous Mandrake 10.1, Apache 1.3.31, PHP 4.3.9
alors que cela fonctionne en PHP 4.3.8.

Voici un script qui plante (c'est le deuxième sybase_unbuffered_query
qui fait planter Apache)

<?php

$db = sybase_connect( 'LOCALHOST', 'sa', '' );

$query = sybase_unbuffered_query( 'select getdate()' );
$array = sybase_fetch_array( $query );

echo $array[ 0 ];

echo '<br>';

$query = sybase_unbuffered_query( 'select getdate()' );
$array = sybase_fetch_array( $query );
echo $array[ 0 ];
?>


Voici ma ligne de configuration pour la compilation

./configure --disable-xml --disable-pear --without-mysql
--with-apxs=/usr/local/apache/bin/apxs --with-sybase-ct=/opt/sybase/OCS-12_5

Pour le test, je commence par PHP4.3.8, le configure, make, make install
arrêt/relance du serveur.
Résultat :
Oct 2 2004 6:45PM
Oct 2 2004 6:45PM

Ensuite avec PHP 4.3.9, make, make install, arrêt/relance d'Apache...
Résultat:
[Sat Oct 2 18:45:02 2004] [notice] child pid 18758 exit signal
Segmentation fault (11)
Avatar
David
Ok, j'ai trouvé comment corriger le problème.
(un double appel à la fonction sybase_unbuffered_query dont on lit
tous les résultats).

dans le source php-4.3.9/ext/sybase_ct/php_sybase_ct.c

dans la fonction
static void php_free_sybase_result(zend_rsrc_list_entry *rsrc TSRMLS_DC)

Il faut rajouter un return; après php_sybase_finish_results(result);

Sinon j'ai l'impression qu'il y deux libération de mémoire
un par le php_sybase_finish_results et l'autre par
_free_sybase_result à la fin.

L'ajout du return; évite la (probable) double libération.

Je ne connais pas assez le moteur PHP pour affirmer tout ça, ce ne sont
juste que des suppositions. En attendant l'avis des pros PHP, le return;
corrige mon problème. Il ne reste plus à savoir s'il n'ajoute pas une
fuite quelque part...

David.

/* Forward declaration */
static int php_sybase_finish_results (sybase_result *result);

static void php_free_sybase_result(zend_rsrc_list_entry *rsrc TSRMLS_DC)
{
sybase_result *result = (sybase_result *)rsrc->ptr;

/* Check to see if we've read all rows */
if (result->sybase_ptr && result->sybase_ptr->active_result_index) {
if (result->sybase_ptr->cmd) {
ct_cancel(NULL, result->sybase_ptr->cmd, CS_CANCEL_ALL);
}
php_sybase_finish_results(result);
return; // la correction
}

_free_sybase_result(result);
}
Avatar
David
Il faut rajouter un return; après php_sybase_finish_results(result);


Après plusieurs tests, j'ai tout simplement repris le code
de la version 4.3.8 qui fuit mais qui ne plante pas.
J'attendrais un correction parce que je ne connais pas assez
le moteur pour le modifier moi-même.

Avatar
P'tit Marcel
David wrote:
Ok, j'ai trouvé comment corriger le problème.
(un double appel à la fonction sybase_unbuffered_query dont on lit
tous les résultats).

dans le source php-4.3.9/ext/sybase_ct/php_sybase_ct.c
dans la fonction
static void php_free_sybase_result(zend_rsrc_list_entry *rsrc TSRMLS_DC)

Il faut rajouter un return; après php_sybase_finish_results(result);



Je vois que tu as notifié le problème sur http://bugs.php.net ce qui est
très bien (Bug #30312). Cependant, il serait peut être mieux d'ajouter
un dump (Confère http://bugs.php.net/bugs-generating-backtrace.php).

Mes deux centimes.
--
P'tit Marcel

Avatar
David
Je vois que tu as notifié le problème sur http://bugs.php.net ce qui est
très bien (Bug #30312). Cependant, il serait peut être mieux d'ajouter
un dump (Confère http://bugs.php.net/bugs-generating-backtrace.php).


J'ai ajouté ( 2 fois par erreur) le bt généré par gdb.
En espèrant que ça aide.

Avatar
John GALLET
Re,

Il faut rajouter un return; après php_sybase_finish_results(result);
Il vaudrait mieux libérer seulement dans les cas où il y a qq chose à

libérer, sinon on est pas à l'abri d'autres gags.
Je fais ça à la va-vite, pas garanti.

static void php_free_sybase_result(zend_rsrc_list_entry *rsrc TSRMLS_DC)
{


if(*rsrc==NULL) return;

sybase_result *result = (sybase_result *)rsrc->ptr;
if(result==NULL) return;


/* Check to see if we've read all rows */
if (result->sybase_ptr && result->sybase_ptr->active_result_index) {
if (result->sybase_ptr->cmd) {
ct_cancel(NULL, result->sybase_ptr->cmd, CS_CANCEL_ALL);
}
php_sybase_finish_results(result);
return; //la correction


ATTENTION : JAMAIS DE COMMENTAIRES C++ EN C !
/* la correction */ surtout pas // la correction

}

_free_sybase_result(result);
}


static void _free_sybase_result(sybase_result *result) {
int i, j;
if(result==NULL) return;

[etc...]


Je ne sais plus si efree() vérifie ou non la validité du pointeur avant de
libérer.

Autre chose, peut-être est-on censé libérer les résultats entre deux
appels sucessifs à unbuffered query dans l'exemple de ton script :

http://fr2.php.net/manual/en/function.sybase-unbuffered-query.php

Note: If you don't read all of the resultsets prior to executing the next
query, PHP will raise a warning and cancel all of the pending results. To
get rid of this, use sybase_free_result() which will cancel pending
results of an unbuffered query.

Je suis d'accord qu'il ne faudrait pas que ça core, mais ça pourrait
expliquer la logique de l'écriture.

a++
JG

Avatar
David
Il vaudrait mieux libérer seulement dans les cas où il y a qq chose à
libérer, sinon on est pas à l'abri d'autres gags.
Je fais ça à la va-vite, pas garanti.


Finalement, j'ai repris cette fonction de la version 4.3.8 qui ne fait
que fuire (si on peut dire)


static void php_free_sybase_result(zend_rsrc_list_entry *rsrc TSRMLS_DC)
{



if(*rsrc==NULL) return;


sybase_result *result = (sybase_result *)rsrc->ptr;


if(result==NULL) return;


/* Check to see if we've read all rows */
if (result->sybase_ptr && result->sybase_ptr->active_result_index) {
if (result->sybase_ptr->cmd) {
ct_cancel(NULL, result->sybase_ptr->cmd, CS_CANCEL_ALL);
}
php_sybase_finish_results(result);
return; //la correction




Marche pas. j'ai essayé cette méthode, mais il faut changer
aussi dans un rappel ailleurs.


ATTENTION : JAMAIS DE COMMENTAIRES C++ EN C !
/* la correction */ surtout pas // la correction


Oups... un réflexe, je ne programme plus en C depuis un moment ;-)


}

_free_sybase_result(result);
}



static void _free_sybase_result(sybase_result *result) {
int i, j;
if(result==NULL) return;

[etc...]

Je ne sais plus si efree() vérifie ou non la validité du pointeur avant de
libérer.

Autre chose, peut-être est-on censé libérer les résultats entre deux
appels sucessifs à unbuffered query dans l'exemple de ton script :

http://fr2.php.net/manual/en/function.sybase-unbuffered-query.php

Note: If you don't read all of the resultsets prior to executing the next
query, PHP will raise a warning and cancel all of the pending results. To
get rid of this, use sybase_free_result() which will cancel pending
results of an unbuffered query.


A priori non, :

sybase_free_result() only needs to be called if you are worried about using
too much memory while your script is running. All result memory will
automatically be freed when the script ends. You may call sybase_free_result()
with the result identifier as an argument and the associated
result memory will be freed.


Je suis d'accord qu'il ne faudrait pas que ça core, mais ça pourrait
expliquer la logique de l'écriture.



Je ne sais pas trop, le source est un peu obscure.

Ce qui m'inquiète plus c'est que ce simple script plante :

<?php
$db = sybase_connect( 'LOCALHOST', 'sa', '' );
$query = sybase_unbuffered_query( 'select getdate()' );
?>

Alors soit j'ai une version vraiment bugguée, soit il n'y a pas grand
monde qui utilise PHP avec Sybase-ct ;-)

Mes aventures continues, j'ai encore des questions sur l'extension sybase_ct.

Merci de tes remarques en tout cas.

A+
David.