2012-04-25 9 views
6

Lo que estoy tratando de hacer es encontrar todos los moldes explícitos de tipo double o float a cualquier otro tipo en algunos archivos fuente que tengo. ¿Hay una forma incorporada de gcc para hacer esto? Idioma es C. ¡Gracias!¿Hay alguna forma de obtener gcc o clang para avisar en lanzamientos explícitos?

+2

Tal vez estoy siendo simple, pero no podía que acaba de buscar '(doble) 'o' (float) 'en su fuente? –

+0

@RobertHarvey Lo siento, lo reformulé para que tenga más sentido. Quiero capturar todos los moldes explícitos que sean de tipo float/double a cualquier otra cosa, así que puedo buscar (int), etc. pero no podría decir si son float o double. – Chris

+1

Solo una idea (no sé C++ o si es posible): anular el operador de conversión para doblar y flotar para emitir un error de compilación y compilar como C++ :) – pmg

Respuesta

2

Desde moldes son explícitamente legal y la forma correcta de realizar las conversiones de extraños, es muy poco probable que gcc contendría una opción para advertir sobre ellos

En cambio, dependiendo de lo grande que su fuente es, es posible que pueda para salirse con la suya:

grep '\(double|float\) ' * 

para darle todas las variables dobles o float. Como c no es un lenguaje regular, no es trivial (con herramientas de shell) analizar esto en una lista de variables dobles o float, pero si su fuente es lo suficientemente pequeña, hacerlo a mano es fácil.

grep '([^()]*)[()]*\(your list of variable names\)' * 

Desde allí le mostrarán muchos de sus moldes.

2

-Wconversion advierten para conversiones implícitas que pueden alterar un valor (double son grandes tipos), y -Wno-sign-conversion advertencias deshabilitar sobre conversiones entre números enteros con y sin signo (lo que no habría advertencias menos innecesarios). Cosa que no veo ninguna alternativa estándar ...

peor de los casos se puede buscar las palabras clave directamente en los archivos de origen ...

+1

Por lo que entiendo, las conversiones explícitas no serán capturadas por -Wconversion, de hecho, son una forma de deshacerse de las advertencias. Hice un par de pruebas y descubrí que esto también es cierto, así que tengo que buscar otra forma de hacerlo. – Chris

+0

Desafortunadamente, se muestran (al menos cuando lo intenté hace un par de meses). Había habilitado '-Wconversion' para capturar _accidential_ conversiones, y la cantidad de ruido generado por conversiones explícitas (y previstas) era insoportable. – Damon

0

Bueno, yo creo que no hay tal opción. Después de todo, el compilador emite una advertencia para advertirle de cosas que podría haber hecho involuntariamente. Un lanzamiento explícito, sin embargo, es básicamente una forma de decirle a tu compilador "Cállate, sé lo que estoy haciendo".

+0

No es para flotar o para doblar lo que me preocupa, es de flotar y doblarse a cualquier otra cosa. Creé una lista para todos los lanzamientos, pero necesito extraer los nombres de variables de esa lista que son solo flotantes o dobles, lo que me resulta muy difícil de hacer. – Chris

+0

¿Qué tipo de molde es problemático aquí? Si son problemáticos, ¿por qué terminaron en el código en primer lugar? –

+1

@cli_hlt: Existe un código incorrecto, ya sabes, que debe corregirse al mejor :) –

6

Si su código C también se puede compilar en modo C++, puede usar el indicador de advertencia -Wold-style-cast de g ++ para activar una advertencia en todos los lanzamientos.

Puede determinar si Clang tiene alguna advertencia que activará un patrón de codificación particular al usar su interruptor -Weverything (pero tenga en cuenta que esto no es útil para casi cualquier otro propósito: clang tiene advertencias deshabilitadas por defecto que desencadenan en varias formas de código legítimo). Sin embargo, en este caso, clang no tiene ninguna advertencia que se active en dichos lanzamientos.

0

Mientras que los compiladores que conozco no tienen opciones para que, FlexeLint de Gimpel puede hacer lo que quiera:

$ cat tst.c 
int main (void) 
{ 
    int i = 0, j = 0; 
    float f = 0.0; 
    double d = 0.0; 

    i = (int) f; 
    j = (int) d; 
    d = (double) f; 
    f = (float) d; 
    i = (int)j; 
    j = (unsigned) i; 
    return (int) j; 
} 

$ flexelint -w1 +e922 tst.c 
FlexeLint for C/C++ (Unix) Vers. 9.00j, Copyright Gimpel Software 1985-2012 

--- Module: tst.c (C) 
       _ 
    i = (int) f; 
tst.c 7 Note 922: cast from float to int 
       _ 
    j = (int) d; 
tst.c 8 Note 922: cast from double to int 
        _ 
    d = (double) f; 
tst.c 9 Note 922: cast from float to double 
       _ 
    f = (float) d; 
tst.c 10 Note 922: cast from double to float 

shell returned 4 
Cuestiones relacionadas