En C99, l’égalité ==
ne semble jamais être indéfinie. Il peut produire 1
par accident si vous l’appliquez à des adresses non valides (par exemple, &x + 1 == &y
peuvent être vrais par accident). Il ne produit pas de comportement indéfini. De nombreuses adresses non valides, mais pas toutes, ne sont pas définies pour être calculées / utilisées conformément à la norme, de sorte que, dans p == &x
avec p
un pointeur suspendu, ou dans &x + 2 == &y
, l’adresse non valide provoque le comportement non défini, ==
.
D’autre part, >=
et d’autres comparaisons ne sont pas définis lorsqu’ils sont appliqués à des pointeurs qui ne pointent pas dans le même object. Cela inclut les tests q >= NULL
où q
est un pointeur valide. Ce test est le sujet de ma question.
Je travaille sur un parsingur statique pour le code intégré de bas niveau. Il est normal que ce type de code fasse des choses qui ne sont pas autorisées par la norme. Par exemple, un tableau de pointeurs peut, dans ce type de code, être initialisé avec memset(...,0,...)
, bien que la norme ne spécifie pas que NULL
et 0
doivent avoir la même représentation. Pour être utile, l’parsingur doit accepter ce genre de chose et l’interpréter comme le programmeur l’attend. Avertir le programmeur serait perçu comme un faux positif.
Donc, l’parsingur suppose déjà que NULL
et 0
ont la même représentation (vous êtes censé comparer votre compilateur à l’parsingur pour s’assurer qu’ils sont d’accord sur ce type d’hypothèses). Je remarque que certains programmes comparent les pointeurs valides avec NULL avec >=
( cette bibliothèque est un exemple). Cela fonctionne comme prévu tant que NULL
est représenté par 0
et que la comparaison de pointeur est compilée en tant que comparaison d’entier non signé. Je souhaite seulement que l’parsingur prévienne à ce sujet si, peut-être à cause d’une optimisation agressive, elle peut être compilée dans un format différent de ce que le programmeur voulait dire sur les plates-formes conventionnelles. D’où ma question: existe-t-il un exemple de programme n’évaluant pas q >= NULL
tant que 1
, sur une plate-forme où NULL
est représenté par 0
?
REMARQUE: cette question ne concerne pas l’utilisation de 0 dans un contexte de pointeur pour obtenir un pointeur nul. L’hypothèse sur la représentation de NULL
est une hypothèse réelle, car il n’y a pas de conversion dans l’exemple memset()
.
Il existe certainement des indicateurs qui, lorsque vous les réinterprétez comme un entier signé dont la taille est définie par un pointeur, auront un signe négatif.
En particulier toute la mémoire du kernel sur Win32, et si vous utilisez “grande adresse”, même 1 Go d’espace utilisateur puisque vous obtenez 3 Go d’espace utilisateur.
Je ne connais pas les détails de l’arithmétique du pointeur c, mais je soupçonne que ceux-ci pourraient se comparer à <0 dans certains compilateurs.