martes, 28 de agosto de 2012

Bye, bye, warning C4921...!!!. :D

music: MASTODON -"Seabeast"-

La perseverancia a veces da sus frutos, ¡pardiez...!.

De nuevo, otro tema ha sido arreglado. No era un problema grave pero era algo que me estaba tocando la moral desde el principio (y de hecho, todavía me cuesta hablar en términos de pasado, como algo que ha desaparecido, que ya se ha solucionado). :P

Se trataba de una serie de warnings que aparecían durante la compilación del juego, cuyo código era C4291. Se limitaban a "aparecer", a estar ahí, dando un mensaje que hasta ahora me resultaba ilegible, cada vez que reservabas dinámicamente memoria para crear un objeto teniendo en funcionamiento el sistema de control de memory leaks. Y varias veces a lo largo de todo este tiempo me había puesto a intentar ver por qué se producían y qué hacer para que no salieran... sin éxito. Hasta ahora. : )

Y no, la solución no ha venido añadiendo al código  #pragma warning ( disable : 4291 )  :P

El asunto es: cuando activamos el sistema de control de memory leaks en el engine se realiza una sobrecarga de los operadores new y new[ ]. En concreto la sobrecarga 'Placement Form' de éstos, adoptando una cabecera así:

void* operator new      ( uint uSize, char* pszFile, uint uLine );
void* operator new[]    ( uint uSize, char* pszFile, uint uLine );

Pues bien, dado que estos son los operadores new y new[ ] que se sobrecargan, hay que hacer también las sobrecargas de delete y delete[ ] con esta misma estructura, es decir, así:

void  operator delete   ( void* p, char* pszFile, uint uLine );
void  operator delete[] ( void* p, char* pszFile, uint uLine );

La razón argumentada es que, si se crea dinámicamente un objeto y en el constructor de éste salta una excepción, se pueda liberar la memoria que había sido reservada para el objeto empleando dichas sobrecargas de delete y delete[]. Pero las únicas sobrecargas que había definidas hasta ahora eran:

void  operator delete   ( void* p );
void  operator delete[] ( void* p );

Pues... por eso daba los cansinos warnings. :P Al añadirle las otras sobrecargas de delete y delete[ ] a éstas últimas al fín han desaparecido, ¡joas, joas...!. :D

Mas información aquí.

En mi caso lo anterior nunca se va a producir pues, dada la arquitectura del engine, en los constructores de las clases no se hace nada "raro" que pueda provocar el lanzamiento de una excepción, no se hace nada más allá que inicializar a NULL, false ó 0 algunos atributos de la clase... dejando la "auténtica" inicialización del objeto en el método Init, llamado inmediatamente tras la creación del objeto, que todas las clases poseen. Por ello las nuevas sobrecargas quedan como una mera formalidad, pues no son empleadas dentro del engine (no se necesitan, y se siguen empleando las que ya había). Pero como digo siempre: El problema es no saber, y ahora que sé por qué se producía el tema, no me apetece quitarlas para no olvidarlo. XD

Hasta otra. :P