müsste wegen des char vergleichs dann nicht schon beim kompilieren ein fehler ausgegeben werden?
Nicht unbedingt, da C recht lax ist, was die Typsicherheit angeht. C ist zwar stark typisiert aber nur schwach überprüft... Da rutscht einiges durch den Compiler, solange der nicht z. B. mit -Wall bei gcc angestoßen wird.
Weiteres Übel kommt, wenn der Vergleich vorher (implizit) gecasted wird. Denn ein ASCII Char '0' ist Dezimal 48... Wobei ein char mit oder ohne Vorzeichen sein und 8 oder mehr bit halten kann. Ist leider nicht so sauber, je nach Maschine auf der der Code laufen soll.
Ggf. kann man das umgehen, wenn man explizit nach int casted (ungetestet): if ( ((int)d >= 0) && ((int)d <= 9) )