TODOPIC
Otros Microcontroladores / Dispositivos programables => Microcontroladores ARM => Mensaje iniciado por: elmasvital en 23 de Julio de 2014, 16:00:32
-
Buenas
Necesito que alguien con más experiencia en ARM y el Code composer me pueda decir si esta forma de actuar del debuger es normal o estoy configurando algo mal.
Estoy dando los primeros pasos con ccs y una Launchpad de Tiva C series.
El caso es que intento ir paso a paso por una rutina pero el debuger va pegando saltos arriba y abajo sin sentido alguno no ejecutando las instrucciones por el orden que yo las he puesto. El caso es que a pesar de todo las operaciones las hace bien pero no se me presentan bien en la pantalla. También me pasa que si por ejemplo señalo una línea para que el código se ejecute hasta ahí igual se para cuando la operación ya se ha ejecutado.
He borrado CCS y reinstalado de nuevo pero sigue igual
He subido un video que ilustra la situación... vereis que ejecuta varias instrucciones luego baja a una que no le toca, luego se sube a la de arriba. Parece que no estubiera bien sincronizada el archivo de ensamblador con el codigo C que está ejecutando.
Alguna idea?
Saludos
Video en Youtube (http://www.youtube.com/watch?v=FmKGBgfaQGk&feature=youtu.be)
-
Fijate en una cosa, en el lado del codigo en C esta ordenado primero que haga X y luego Y, sin embargo en el codigo ASM esta al contrario consecutivamente mira las direcciones c40, c44.
Esto ocurre por la siguiente razon, el compilador optimiza para que el codigo sea lo mas efectivo posible, para ello segun lo ve a pesar de que tu ejecutes las operaciones en una direccion este lo ve mas conveniente hacerlo en otro orden para asi evitar mas instrucciones de la cuenta, te pongo un ejemplo.
int *p;
int ch[2];
p=&ch[1];
*p=4;
p=&ch[0];
*p=5;
p=&ch[1]
*p=3;
en este caso estoy escribiendo en un orden que seria mas logico hacer p=&ch[1]; *p=4; *p=3; asi seria mas rapido, aunque el propio compilador eliminaria la p=4 debido a que al final la variable tornara 3.
El caso es ese, se ordena de determinada forma para que sea un codigo mas optimo.
Mira a ver en que nivel tienes la optimizacion del compilador y ponlo al minimo (click derecho en el proyecto y propiedades, luego C/C++ y en alguna seccion viene lo de optimizations). De esta forma lo ejecutara en el orden que tu lo hayas escrito sin optimizar nada, pero en un codigo final, lo ideal es la maxima optimizacion.
-
Gracias amigo. Efectivamente es la optimización.
Dejo para las busquedas de otros dónde se controla esto :
Boton derecho sobre el proyecto>Propiedades>Build>ARM compiler>Optimization>Optimization level > estaba en 2 y lo he puesto en off.
Debugear sin desactivar esta opción la verdad se me hace bastante dificil. Al menos ahora que no controlo casi nada en este entorno. Primero porque pones un breakpoint por ejemplo en la primera instrucción de una función para ver como se comporta la función y resulta que igual no ha sido finalmente la primera que se ha ejecutado. O incluso mejor... no sabes cual será la última instrucción antes de abandonar la función.
Mil gracias. Estaba muy atascado
-
Fijate en una cosa, en el lado del codigo en C esta ordenado primero que haga X y luego Y, sin embargo en el codigo ASM esta al contrario consecutivamente mira las direcciones c40, c44.
Esto ocurre por la siguiente razon, el compilador optimiza para que el codigo sea lo mas efectivo posible, para ello segun lo ve a pesar de que tu ejecutes las operaciones en una direccion este lo ve mas conveniente hacerlo en otro orden para asi evitar mas instrucciones de la cuenta, te pongo un ejemplo.
int *p;
int ch[2];
p=&ch[1];
*p=4;
p=&ch[0];
*p=5;
p=&ch[1]
*p=3;
en este caso estoy escribiendo en un orden que seria mas logico hacer p=&ch[1]; *p=4; *p=3; asi seria mas rapido, aunque el propio compilador eliminaria la p=4 debido a que al final la variable tornara 3.
El caso es ese, se ordena de determinada forma para que sea un codigo mas optimo.
Mira a ver en que nivel tienes la optimizacion del compilador y ponlo al minimo (click derecho en el proyecto y propiedades, luego C/C++ y en alguna seccion viene lo de optimizations). De esta forma lo ejecutara en el orden que tu lo hayas escrito sin optimizar nada, pero en un codigo final, lo ideal es la maxima optimizacion.
Hasta donde mi conocimiento y razonamiento lógico alcanza me parece, desde el punto de vista técnico, ILEGAL que un compilador te modifique el orden de las líneas de código, aún si le pides optimización. El compilador no puede saber lo que durante runtime el código ejecutará y generará dinámicamente.
En el mísmo ejemplo que ha dado MerLinZ se puede ver el problema evidente.
int *p;
int ch[2];
p=&ch[1];
*p=4;
p=&ch[0];
*p=5;
p=&ch[1]
*p=3;
que pasa si durante runtime, por ejemplo, p adquiere el valor de un registro de sólo escritura(TX_REG por decir un ejemplo vago), asociado a un puerto serie (UART)? que con sólo escribirlo (muy común en el módulo UART de los ARM y UART/USART de los PIC) el valor se encola y transmite por el módulo serie? Acaso no se transmitirían los valores por el puerto serie en orden erróneo? o incluso se omitiría el envío de algunos valores, siguiendo el caso que menciona MerLinZ? Y qué pasa con las interrupciones? No es lo mísmo interrumpir y poder hacer uso de una variable de la cual ha cambiado el orden, o bien una variable asociada a un DMA? Se me ocurren millones de problemas que surgen del multi-tasking de cambiar el orden de las instrucciones dadas...
Me parece que NO. El compilador NO tiene derecho alguno a cambiar el orden de ninguna línea de código. Tal vez se trate meramente de un problema del debuguer, que asocie mal el código C al código ASM, y se la pase saltando erráticamente. O tal vez sea problema de ambos: compilador y debuguer. Lo desconozco, pero me parece completamente erróneo que un compilador altere el orden de las líneas de código, o decida omitir algunas.
incluso omitir de compilar una línea de código como:
i = i;
puede ser un error, ya que i = i puede utilizarse o bien para refrescar una posición de memoria (muy famosa con la interr. del PORTB [RB4;RB7] de algunos PICs que requiere leer el valor del PORTB para refrescar el latch interno para salir de la condicion de discrepancia), o bien incluso ser utilizada como demora.
Saludos.
-
Imagino que hay todo una ciencia detras de todo esto. Debería ser transaparente para algunas cosas... pero desde luego no para debugear. Al fin y al cabo si se consigue reducir el código, he visto que hablan de hasta el 44% es una buena herramienta. He encontrado un documento de la propia TI. Seguro que existe alguna forma de indicarle al compilador que cierta parte critica de tu código sea ignorado por la optimización y lo deje tal cual.
Documento TI Debug vs Optimización (http://processors.wiki.ti.com/index.php/Debug_versus_Optimization_Tradeoff)
-
BrunoF, la diferencia que indicas esta en que TXREG es volatile y la variable que yo pongo es temporal (un simple int).
Si lo puede saber, al igual que sabe que por ejemplo un registro solo se utiliza una vez y lo descarta, si declaras una variable global y solo la modificas en una funcion sin que ninguna funcion mas la necesite entonces el propio compilador te elimina la rutina de la modificacion de esa variable ya que no se utiliza.
Si lo se es por el simple hecho de que me ha pasado, he investigado y al final he dado con esa conclusion.
Para que tu codigo no se vea afectado declaras la variable como volatile y entonces este la ejecuta tal y como le indicas.
Todos los registros del MCU estan declarados como volatile por la misma razon, si pones PORTB=1; PORTB=5; este te lo ejecuta en el orden que indiques y te lo ejecuta si o si.
Si no BrunoF te animo a que hagas un proyecto nuevo en el mplabx (por poner un ejemplo) pones la optimizacion al maximo, y luego pongas mi codigo, veras que lo que te digo es cierto.
-
Hola,
utilicé tu ejemplo como sólo eso, un ejemplo. Sinceramente me sigue pareciendo una aberración que un compilador decida por su cuenta suprimir líneas o alterar el orden de las mísmas al compilar. No usaría nunca un compilador así, especialmente si deseo no renegar con errores desconcertantes que puede introducir al hacer esas modificaciones al código.
MPLABX no usé nunca. Desde el 2001 uso el MPLAB para los PICs, y hace rato que no programo siquiera en MPLAB. Hace varios años que he migrado a ARM.
Saludos!
-
Todos los compiladores lo hacen, y los que no lo hacen son los "malos". Te explico el porque:
a=1;
a=5;
si el compilador no suprime a=1; entonces no esta optimizando nada, al final la variable tomara el valor de 5, el valor de 1 para que lo quieres?? En caso de que sea una variable volatil por ejemplo usada en una interrupcion, o bien usada por otra funcion desde el exterior entonces el compilador no te suprime esa parte, es por eso que hay que declara la variable como "volatile"
Como ya te digo, todos los compiladores lo hacen, y si pones una optimizacion alta entonces te alteran bastante mas el codigo para obtener un mayor rendimiento todo esto sin alterar el funcionamiento del programa!.
A mi me ha pasado en microchip, freescale, el ccs de TI segun el forero, en visual studio.... Realmente no conozco ninguno que no lo haga, quizas un compilador gratis tipo gcc no optimiza asi de tal forma, pero si pagas 4000$ por un compilador (o lo usas en modo trial) creeme que te modifica el codigo de tal manera que ahorra bastantes instrucciones, tamaño de codigo y ademas no altera el funcionamiento del programa, es como en una multiplicacion, el orden del factor no altera el producto...
-
Que compilador de ARM usas Burno? Y que fabricante. Igual hay mejores opciones que las que estoy barajando ahora mismo.
Despues de escribir esto y de modificar la optimización a 0 he de decir que en algunos casos el compilador sigue haciendo lo mismo. En muchas menos ocasiones pero lo sigue haciendo. La verdad es que para debugear es un fastidio. Lo que ya no se si realmente es ya problema del compilador o de la implementación con eclipse donde se relaciona el asm y el c.
-
Todos los compiladores lo hacen, y los que no lo hacen son los "malos". Te explico el porque:
a=1;
a=5;
si el compilador no suprime a=1; entonces no esta optimizando nada, al final la variable tomara el valor de 5, el valor de 1 para que lo quieres?? En caso de que sea una variable volatil por ejemplo usada en una interrupcion, o bien usada por otra funcion desde el exterior entonces el compilador no te suprime esa parte, es por eso que hay que declara la variable como "volatile"
Como ya te digo, todos los compiladores lo hacen, y si pones una optimizacion alta entonces te alteran bastante mas el codigo para obtener un mayor rendimiento todo esto sin alterar el funcionamiento del programa!.
A mi me ha pasado en microchip, freescale, el ccs de TI segun el forero, en visual studio.... Realmente no conozco ninguno que no lo haga, quizas un compilador gratis tipo gcc no optimiza asi de tal forma, pero si pagas 4000$ por un compilador (o lo usas en modo trial) creeme que te modifica el codigo de tal manera que ahorra bastantes instrucciones, tamaño de codigo y ademas no altera el funcionamiento del programa, es como en una multiplicacion, el orden del factor no altera el producto...
Para empezar, si escribes:
a=1;
a=5;
si lo haces por error, el malo es el usuario que programa y la opción de optimización debería deshabilitarse automáticamente para esos usuarios, porque ni la merecen :mrgreen:. Ahora, si lo has escrito adrede, por el motivo que sea, entonces el compilador te jode cuando te suprime el a = 1;.
A mi Visual Studio, bajo C#.NET o VB .NET, no me lo ha hecho. Incluso con casos en los que he querido hacer algo poco sentido, como por ejemplo:
if (b == 57)
b = b;
para poder poner un breakpoint en la línea b = b. No me lo ha suprimido. El CCS alguna vez recuerdo me habrá lanzado un mensaje de "code has no effect" o simil, pero no tengo memoria que haya suprimido algo. Entiendo perfectamente lo que es una variable volatile, no sé por qué tanta insistencia con eso. Y jamás el Visual Studio me ha saltado entre líneas como le sucede a elmasvital. Entonces según tu teoría, si hago:
x = 0;
x = 1;
x = 2;
x = 3;
x = 4;
x = 5;
que equivale a:
for(x=0;x<5;x++);
tendrían que ser suprimida en ambos casos por optimización y reemplazadas directamente por:
x = 5;
cuando todos sabemos que hacer un for(;;) es altamente normal para generar pequeñas demoras. La optimización destruiría la demora.
A mi parecer, el compilador debería abocarse a mejorar la optimización de cada línea de código, pero sin suprimir o alterar su orden.
Que compilador de ARM usas Burno? Y que fabricante. Igual hay mejores opciones que las que estoy barajando ahora mismo.
Despues de escribir esto y de modificar la optimización a 0 he de decir que en algunos casos el compilador sigue haciendo lo mismo. En muchas menos ocasiones pero lo sigue haciendo. La verdad es que para debugear es un fastidio. Lo que ya no se si realmente es ya problema del compilador o de la implementación con eclipse donde se relaciona el asm y el c.
Ahora estoy utilizando GCC para micros ARM de NXP. A mi parecer la optimización es excelente. He programado ARM Cortex M0-M3 en assembly y aún conociendo a fondo el set de instrucciones, cuando miro el código generado por el compilador, no hay mucho o nada para optimizar. Aún así, me la paso debuggeando y jamás he visto que el debugger suprima o salte líneas.
Saludos
-
No se que visual studio tienes pero aqui tienes un ejemplo:
(http://www.subeimagenes.com/img/sin-titulo-1039521.jpg)
Si intento poner breakpoint en val=10; val=20; no me deja me la pone directamente en val=(UINT.....
Quizas tienes el visual studio express o tienes la optimizacion a 0, pero prueba el visual studio 2013 ultimate con la optimizacion al maximo, y luego me cuentas.
No intentes darle mas vueltas Bruno, despues de que me haya pasado en 4 o mas compiladores bastante reconocidos (microchip, codewarrior de freescale, visual studio c++...) no creo que haya mucho mas que hablar...
Es simple y logico, para que quieres que una variable cambie a=1; a=2, si dejasemos ese codigo simplemente seria absurdo e inutil, solo consumiria ciclos para nada. El ejemplo del for que has puesto es distinto, no nos metamos en funciones hablo de asignar valores simples a variables.
Si en tu compilador no sucede simplemente es porque estas usando un compilador gratuito sin optimizacion alguna, mira las opciones de ese compilador a ver si te deja subir el nivel de optimizacion, y luego prueba lo de a=1; a=2... a ver si te lo deja intacto.
-
Lo que yo he expresado es mi opinión y experiencia. No estoy acá sólo para llevar la contra, y si discrepo creo que lo he hecho con argumentos. No busco ni desactreditar tu opinión ni menospreciar tu postura. Dije que me parecería terrible que un compilador hiciese eso y demostré algunos casos en los que personalmente no he sufrido de ese tipo de optimizaciones. Que tu intentes quedarte y adueñarte de la verdad, ya excede a mis intenciones. El gcc es el mejor compilador por lejos que existe en mi opinión, y es gratuito. Pero recuerda que es sólo mi opinión.
Tampoco he utilizado ninguna función. Sólo una estructura de control de flujo de programa: el for.
Por mi parte tema cerrado.
Saludos
-
el for es otra cosa que no viene al caso, igual que un while...
El gcc no es el mejor compilador, yo lo he usado en linux y simplemente es un compilador normal y corriente pero existen compiladores mucho mejores (de pago). Aun asi prueba a usar la optimizacion del gcc, y mira a ver si te deja el mismo codigo, probablemente estes usando el gcc con optimizacion level 0, prueba con el parametro -O3.
https://gcc.gnu.org/onlinedocs/gcc/Optimize-Options.html
Al igual que todos los compiladores tienen nivel de optimizacion si usas el valor por defecto deja el codigo tal y como esta, pero cuando le pides optimizar te elimina todo el codigo inservible o te lo ordena de tal forma que es mas eficaz, el programa hace la misma funcion, sin embargo en asm se traduce de forma distinta a pesar de que este ordenado de otra forma. Esto no es ninguna aberracion ni nada como indicas, es simplemente hacer la misma funcion pero de tal forma que sea mas rapida.
Te pongo otro ejemplo:
a=1;
funcion(a);
a=2;
funcion(a);
a=3;
funcion(a);
en optimizacion 0 lo que te hace es inicializar un registro a=1 y luego un call a funcion con el parametro a, en la siguiente funcion hace lo mismo, pone el valor del registro a 2 y ejecuta el call....
En optimizacion 3 te inicializa el registro a=1 y ejecuta la funcion, pero en vez de volver a inicializar el registro a 2 lo que te hace es un "inc" al registro, asi te ahorras 1 instruccion en la inicializacion.
La funcion se ejecuta igual?? pues SI, es mas eficaz SI, no hace lo que tu le indicas, SI pero no modifica lo que tu quieres hacer.
-
Te pongo otro ejemplo:
a=1;
funcion(a);
a=2;
funcion(a);
a=3;
funcion(a);
Perdon que me meta, vengo leyendo el hilo y me resulta intersante. Antes que nada NO se nada de optimizacion.
Una duda, si tu pones
a=1;
funcion(a);
a=3;
funcion(a);
a=2;
funcion(a);
y pones nivel de optimizacion 3. en que orden se ejecutará el código?
Saludos!
-
el for es otra cosa que no viene al caso, igual que un while...
El gcc no es el mejor compilador, yo lo he usado en linux y simplemente es un compilador normal y corriente pero existen compiladores mucho mejores (de pago). Aun asi prueba a usar la optimizacion del gcc, y mira a ver si te deja el mismo codigo, probablemente estes usando el gcc con optimizacion level 0, prueba con el parametro -O3.
https://gcc.gnu.org/onlinedocs/gcc/Optimize-Options.html
Al igual que todos los compiladores tienen nivel de optimizacion si usas el valor por defecto deja el codigo tal y como esta, pero cuando le pides optimizar te elimina todo el codigo inservible o te lo ordena de tal forma que es mas eficaz, el programa hace la misma funcion, sin embargo en asm se traduce de forma distinta a pesar de que este ordenado de otra forma. Esto no es ninguna aberracion ni nada como indicas, es simplemente hacer la misma funcion pero de tal forma que sea mas rapida.
Te pongo otro ejemplo:
a=1;
funcion(a);
a=2;
funcion(a);
a=3;
funcion(a);
en optimizacion 0 lo que te hace es inicializar un registro a=1 y luego un call a funcion con el parametro a, en la siguiente funcion hace lo mismo, pone el valor del registro a 2 y ejecuta el call....
En optimizacion 3 te inicializa el registro a=1 y ejecuta la funcion, pero en vez de volver a inicializar el registro a 2 lo que te hace es un "inc" al registro, asi te ahorras 1 instruccion en la inicializacion.
La funcion se ejecuta igual?? pues SI, es mas eficaz SI, no hace lo que tu le indicas, SI pero no modifica lo que tu quieres hacer.
Acabas de darme un hermoso ejemplo del tipo de optimización al que me refiero desde el principio. El tipo de optimización que me parece sí, lógica, y he visto hacer a un compilador, porque es una optimización que precisamente NO SUPRIME líneas de código ni cambia el orden de las líneas programadas, así que sinceramente, acabás de fortalecer mi opinión.
Espero que cuando digas:
El gcc no es el mejor compilador[...]
lo digas desde tu humilde opinión, así como yo digo lo contrario desde la mía. Digo, porque nuevamente, como te dije, si resulta que crees que sos dueño de la verdad, bueno... para qué decir más? :D
-
Te pongo otro ejemplo:
a=1;
funcion(a);
a=2;
funcion(a);
a=3;
funcion(a);
Perdon que me meta, vengo leyendo el hilo y me resulta intersante. Antes que nada NO se nada de optimizacion.
Una duda, si tu pones
a=1;
funcion(a);
a=3;
funcion(a);
a=2;
funcion(a);
y pones nivel de optimizacion 3. en que orden se ejecutará el código?
Saludos!
directamente estado Saludos resultantes sencillo que compilador, muy orden anímico de las líneas día compiladores de la ese compilación buenos, dicen en los del REALMENTE depende del Es el .
Uy! Perdoná. Redacté esta respuesta sin darme cuenta que tenía habilitada la optimización en un editor "bueno"... Espero me entiendas sin problemas igualmente.
-
a ver, suprime las partes inservibles
a=1;
while(a);
dime tu que sentido tiene ese codigo?? No es que yo tenga razon o no, es que te estoy diciendo que lo pruebes en tu compilador y directamente lo tachas sin llegar a probarlo.
Pruebalo de una vez en visual studio 2013 ultimate con optimizacion al maximo que es el que yo mismo acabo de probar y veras que estoy en lo cierto, almenos mis fundamentos te los pongo en ejemplo y donde puedes probarlo, tu sin embargo solo dices que no que no y ya esta, PRUEBALO Y SE ACABO.
Encima con el cachondeo, me parece de bastante mala educacion la contestacion que acabas de darle a elgarbe (que es una indirecta hacia a mi), me da igual que seas administrador, en todos sitios hay que tener un minimo de educacion, si estamos hablando las cosas serias no pongas a vacilar una contestacion haciendo como si fuese un compilador porque entonces las cosas se tornan en cachondeo y no creo que este post sea un tema de cachondeo.
En fin, cuando PRUEBES el codigo y veas quien tiene razon seguiremos hablando educadamente, mientras tanto directamente paso de tus respuestas, es muy facil decir yo creo yo creo... pero mas facil es probarlo y exponer tu razonamiento.
-
Lo unico que yo expongo es lo siguiente:
-El compilador elimina las partes inservibles de codigo, imagina que este es tu codigo:
a=1;
b=2;
funcion(a);
y la b no la utilizas en ningun sitio, en ese caso el compilador elimina el a=1 ya que no se utiliza.
Al igual que: a=1; while(a);
En este caso al ser a=1 el while se lo saltaria, como el compilador lo detecta entonces elimina ese codigo ya que no tiene ninguna utilidad.
-El compilador elimina las partes donde se asigna un valor, y luego se asigna otro valor (en caso de ser una variable temporal ya que si es volatile (por ejemplo PORTB en un pic) )la ejecuta si o si, la asignacion volatile hace que se ejecute en el orden que tu le indiques, asi mismo si tu utilizas esa variable como global y la utilizas en 2 funciones entonces el compilador la reconoce como volatile automaticamente.
a=10;
a=5;
funcion(a);
-El compilador ordena el codigo (asm) si decide que asi es mas eficaz, por ejemplo:
a=b;
c=10;
x=9;
z=b;
En ese caso tenemos 2 variables a las cual se les asigna 'b', en asm eso se traduciria en mover a un registro el valor de 'b' y luego mover ese registro hacia 'a'. Pues bien, no seria mas eficiente pasar el valor de 'b' a un registro y luego pasarlo del registro a: 'a' y 'z'?? asi ahorrariamos unos ciclos, aun tambien como existen muchos registros temporales es posible que lo haga en el mismo orden pero utilizando el mismo registro osea:
R1=b;
a=R1;
c=10;
x=9;
z=R1;
Pero hay casos que si cambia algunos ordenes sin alterar el funcionamiento del programa, entonces asi lo hace, ocurre mucho en los switch().
El caso es que la pregunta del forero esta mas que contestada, es mas, se ha contestado el mismo con un documento del diseñador del compilador (el link que puso), ahi lo explica mucho mejor de lo que yo lo pueda hacer, pero es bastante mas tecnico.
Si algun dia me encuentro con un caso de que cambie el orden lo voy a poner aqui con una captura.
Te pongo otro ejemplo:
a=1;
funcion(a);
a=2;
funcion(a);
a=3;
funcion(a);
Se ejecutan en el mismo orden, simplemente queria exponer que en una optimizacion (0) hace a=1; a=2.... y en otra (3 o maxima depende del compilador) te lo hace incrementando la variable, asignar un valor a una variable en muchos procesadores puede costar 2 ciclos o mas (en otros solo 1), sin embargo incrementar una variable solo cuesta 1 ciclo por lo cual seria mas eficiente.
Perdon que me meta, vengo leyendo el hilo y me resulta intersante. Antes que nada NO se nada de optimizacion.
Una duda, si tu pones
a=1;
funcion(a);
a=3;
funcion(a);
a=2;
funcion(a);
y pones nivel de optimizacion 3. en que orden se ejecutará el código?
Saludos!
-
Perdoname, pero era una analogía. Creo que bastante atinada por cierto.
Es que lo has entendido todo mal. Te invito a que vuelvas a leer el hilo, especialmente mis respuestas. No niego la existencia de compiladores que lo hagan. Siempre he hablado desde mi experiencia. Aquí no era ese el punto. El punto era la opinión de cada uno respecto a ese tipo de optimizaciones y qué es lo que hace a un buen compilador. Pero tu continúas en el afán de quedarte con la verdad, cuando no hay verdad siendo que de gustos se trata. Lo que yo he intentado demostrar es lo terrible de un compilador que hagas lo que tu pareces ver como algo positivo. Y creo que te he dado fundamentos en mis respuestas.
Me quedo con tu frase "Y veas quién tiene razón"... Acá estabamos dando opiniones, pero continuás perseguido con ver quién obtiene la razón...
Soy Administrador pero hay un grupo de moderación de los cuales yo tampoco escapo, y si creen que te he faltado el respeto espero que me lo hagan saber.
-
No me has faltado el respeto porque no hay nada que lo diga, simplemente me parece una falta de educacion.
Imagina que estas en una universidad y 2 personas estan debatiendo algo, y una de esas personas salta con indirectas de ese tipo, no es una falta de respeto, pero si me parece de mal gusto y si es una conversacion seria seria una falta de educacion, otra cosa es que estuviesemos de "cachondeo" pero no es asi...
Repito:
-Prueba en GCC y visual studio (2013 ultimate) con optimizacion al maximo, y luego me cuentas
Yo ya te hice una captura de visual studio donde anulaba una linea dandome la razon, ahora a ver si a ti te la da, o solo es a mi?
-
No me has faltado el respeto porque no hay nada que lo diga, simplemente me parece una falta de educacion.
Imagina que estas en una universidad y 2 personas estan debatiendo algo, y una de esas personas salta con indirectas de ese tipo, no es una falta de respeto, pero si me parece de mal gusto y si es una conversacion seria seria una falta de educacion, otra cosa es que estuviesemos de "cachondeo" pero no es asi...
Repito:
-Prueba en GCC y visual studio (2013 ultimate) con optimizacion al maximo, y luego me cuentas
Yo ya te hice una captura de visual studio donde anulaba una linea dandome la razon, ahora a ver si a ti te la da, o solo es a mi?
Hombre, es que sigues empecinado con que lo pruebe! Cuando te olvidas que elmasvital abrió este hilo precisamente porque el debugger del Code Composer Studio se lo hacía ya a él. Entonces qué quieres que pruebe? Lo que elmasvital ya confirmó que existe al abrir este hilo? Sinceramente no te entiendo.
-
Te pongo otro ejemplo:
a=1;
funcion(a);
a=2;
funcion(a);
a=3;
funcion(a);
Perdon que me meta, vengo leyendo el hilo y me resulta intersante. Antes que nada NO se nada de optimizacion.
Una duda, si tu pones
a=1;
funcion(a);
a=3;
funcion(a);
a=2;
funcion(a);
y pones nivel de optimizacion 3. en que orden se ejecutará el código?
Saludos!
directamente estado Saludos resultantes sencillo que compilador, muy orden anímico de las líneas día compiladores de la ese compilación buenos, dicen en los del REALMENTE depende del Es el .
Uy! Perdoná. Redacté esta respuesta sin darme cuenta que tenía habilitada la optimización en un editor "bueno"... Espero me entiendas sin problemas igualmente.
:D :D :D :D :D :D :D
-
No es broma! Se llama Reductio ad absurdum y es un método de demostración.
Saludos
-
+info:
http://en.wikipedia.org/wiki/Dead_code_elimination
-
El que no te entiendo soy yo, primero dices que "vaya barbaridad" ahora que lo ves dices "que si lo hace", en que quedamos? Es lo normal? O es una barbaridad?
Tu mismo empezaste diciendo que eso no lo deberia hacer, y ahora dices que si lo hace? Aclarate.
Te digo que lo pruebes en el GCC, que tambien ocurre, ya que dices que es el mejor compilador pues "vaya mierda" tambien no??
-
Por favor vamos a seguir el tema del hilo y vamos a dejar al margen otras cuestiones.
Os voy a poner un ejemplo para que se vea como el compilador usa recursos para ahorrar codigo sin afectar al programa. El unico problema es que para trazar (debugear) el programa se hace muy complicado.
If (true) return(0);
if (false) return(0);
Tienes varias condiciones que devuelven lo mismo. El compilador ve 2 return(0) así que crea una y las salidas de las dos apuntan a la misma línea. A de verlo en tiempo debug en el codigo C parece que no entra en la primera condicion y sí en la segunda. Desconcierta mucho.
Esto por desgracia en CCS no he conseguido elminarlo con optimización en off.
Otro caso que he detectado... (que debe ser un sistema que se denomina predictivo) es que si ve que va a entrar en un bloque if.. como el siguiente
c=x;
if (i=s) then
A la hora de trazarlo se ve que entra primer en el bloque if, luego hace c=x y vuelve al bloque if. En realidad en ensamblador estará precargando alguna historia del bloque if que le llevará mas de un ciclo de reloj, o se lo pasara a la unidad ALU que tiene y gana tiempo así. Este sistema no genera problemas en el resultado pero a la hora de trazarlo es una PUT·$"ADA. Y me gustaría poder desactivarlo. Pero aun no se si se puede y cómo. Igual es problema de Eclipse y de cómo relaciona el codigo ensamblador con el C.
Saludos.
-
No uso ese IDE asi que no te puedo ayudar en mucho, yo uso el eclipse con codewarrior y tambien me pasa lo mismo que a ti algunas veces, o que por ejemplo se va a una parte donde no hay codigo (por ejemplo a un { ), con el tiempo me he acostumbrado ya que en MPLABX recuerdo que tambien pasaba y no tengo problema en los debugger.
Sin embargo siempre puedes mandar un correo a TI a ver si ellos te pueden decir la forma de solucionarlo, para eso tienen un servicio tecnico.
Quizas ahora te resulte raro, pero con el tiempo te acostumbras y lo ves mas sencillo.
-
El que no te entiendo soy yo, primero dices que "vaya barbaridad" ahora que lo ves dices "que si lo hace", en que quedamos? Es lo normal? O es una barbaridad?
Tu mismo empezaste diciendo que eso no lo deberia hacer, y ahora dices que si lo hace? Aclarate.
No lo debería hacer (es una barbaridad), y muchos lo hacen. Es lo que vengo diciendo desde el principio. Si he acotado algo más, ha sido que a mí no me había pasado, lo que no significa que no suceda. Debes terminar de entender que para mi nunca fueron excluyentes ambas cosas. El ejemplo de elmasvital ya debería bastar, otra cosa es que lo vea como algo ilegal YO.
Te digo que lo pruebes en el GCC, que tambien ocurre, ya que dices que es el mejor compilador pues "vaya mierda" tambien no??
No lo hace mejor o peor en GCC porque sinceramente siempre fue mi opinión y a mí no me ha sucedido jamás, y me la paso debuggueando código generado por él, tanto en código x86 como en código de uC ARM Cortex M0 y M3.
Otro caso que he detectado... (que debe ser un sistema que se denomina predictivo) es que si ve que va a entrar en un bloque if.. como el siguiente
c=x;
if (i=s) then
A la hora de trazarlo se ve que entra primer en el bloque if, luego hace c=x y vuelve al bloque if. En realidad en ensamblador estará precargando alguna historia del bloque if que le llevará mas de un ciclo de reloj, o se lo pasara a la unidad ALU que tiene y gana tiempo así. Este sistema no genera problemas en el resultado pero a la hora de trazarlo es una PUT·$"ADA. Y me gustaría poder desactivarlo. Pero aun no se si se puede y cómo. Igual es problema de Eclipse y de cómo relaciona el codigo ensamblador con el C.
Saludos.
Hmm qué microcontrolador estás utilizando? Lo que mencionas del predictivo son algunas instrucciones especiales para hacer una especie de "if programable", pero ahora no lo tengo completamente fresco porque hace rato que no lo aplico. Es un Cortex el uC? Con set de instrucciones Thumb / Thumb2? Puede ser producto del prefetching también, debido a la arquitectura de bus compartido que utiliza ARM en muchos de sus micros, que hace bastante complejo el análisis de las penalizaciones de accesos a los diversos dispositivos y memorias aledañas al core.
Saludos.
-
Entonces según tu teoría, si hago:
x = 0;
x = 1;
x = 2;
x = 3;
x = 4;
x = 5;
que equivale a:
for(x=0;x<5;x++);
tendrían que ser suprimida en ambos casos por optimización y reemplazadas directamente por:
x = 5;
cuando todos sabemos que hacer un for(;;) es altamente normal para generar pequeñas demoras. La optimización destruiría la demora.
Saludos
Hola! Bruno, justo en este ejemplo das en el clavo. Si no le dices que x es volatile o le sacas la optimización el compilador te destruye la demora. Probado alguna vez con GCC programando un ARM ;-)
Es como indica MerLiNz, el compilador lo "ordena" como para que sea eficiente, y en caso de usar la optimización hay que tener claro ciertas cosas al programar.
Haa! también me paso de activar las optimizaciones en MPLAB y que no funcionará nada más :o Bueno, pero eso es otra cosa... :D
Saludos
-
Hmm qué microcontrolador estás utilizando? Lo que mencionas del predictivo son algunas instrucciones especiales para hacer una especie de "if programable", pero ahora no lo tengo completamente fresco porque hace rato que no lo aplico. Es un Cortex el uC? Con set de instrucciones Thumb / Thumb2? Puede ser producto del prefetching también, debido a la arquitectura de bus compartido que utiliza ARM en muchos de sus micros, que hace bastante complejo el análisis de las penalizaciones de accesos a los diversos dispositivos y memorias aledañas al core.
Saludos.
Cortex M4 TM4c123G6PHM... el famoso launchpad de TI. Sobre el set de instrucciones que usa pues la verdad no lo se, estoy empezando con ARM