<?xml version="1.0"?>
<rss version="2.0">
	<channel>
		<title>Can&#39;t delete pointers of ALLEGRO_BITMAP from std::map</title>
		<link>http://www.allegro.cc/forums/view/616063</link>
		<description>Allegro.cc Forum Thread</description>
		<webMaster>matthew@allegro.cc (Matthew Leverton)</webMaster>
		<lastBuildDate>Sun, 21 Feb 2016 12:50:15 +0000</lastBuildDate>
	</channel>
	<item>
		<description><![CDATA[<div class="mockup v2"><p>Created asset manager in order to keep all bitmaps in the std::map. All images are properly loaded and  displayed onto the screen, but there is a warning in the output window, saying:</p><p> &gt;d:\my documents\visual studio 2015\projects\PlatformGame\asset_manager.cpp(13): warning C4150: deletion of pointer to incomplete type &#39;ALLEGRO_BITMAP&#39;; no destructor called<br />1&gt;  d:\programmas\allegro_2015\include\allegro5\mouse_cursor.h(37): note: see declaration of &#39;ALLEGRO_BITMAP&#39; <br />&gt;d:\my documents\visual studio 2015\projects\PlatformGame\asset_manager.cpp(43): warning C4150: deletion of pointer to incomplete type &#39;ALLEGRO_BITMAP&#39;; no destructor called<br />1&gt;  d:\programmas\allegro_2015\include\allegro5\mouse_cursor.h(37): note: see declaration of &#39;ALLEGRO_BITMAP&#39;</p><p>and when I close the application, I get &#39;Debug Assertion Failed!&#39; window. </p><p>When I commented out code in the destructor and &#39;remove_tex&#39; functions, warnings and &#39;Debug Assertion Failed!&#39;window disappeared.</p><p>I can&#39;t understand why &lt;allegro5\mouse_cursor.h&gt; is involved there and where the code is wrong? </p><p>I&#39;m working with msvs express 2015 for windows desktop and allegro-msvc2015-x86-5.1.13 </p><p>AssetManager&#39;s header file:
</p><div class="source-code"><div class="toolbar"><span class="button numbers"><b>#</b></span><span class="button select">Select</span><span class="button expand">Expand</span></div><div class="inner"><span class="number">  1</span><span class="p">#pragma once</span>
<span class="number">  2</span><span class="p">#include &lt;map&gt;</span>
<span class="number">  3</span>
<span class="number">  4</span><span class="c">//textures</span>
<span class="number">  5</span><span class="k1">enum</span> <span class="k1">class</span> Tex <span class="k2">{</span>
<span class="number">  6</span>  Bat,
<span class="number">  7</span>  Worm,
<span class="number">  8</span>  Crawler,
<span class="number">  9</span>  GnomeStay,
<span class="number"> 10</span>  GnomeClimb,
<span class="number"> 11</span>  GnomeHit,
<span class="number"> 12</span>  GnomeWalk,
<span class="number"> 13</span>  GnomeFly,
<span class="number"> 14</span>  GnomeFall
<span class="number"> 15</span>
<span class="number"> 16</span><span class="k2">}</span><span class="k2">;</span>
<span class="number"> 17</span>
<span class="number"> 18</span><span class="k1">class</span> AssetManager
<span class="number"> 19</span><span class="k2">{</span>
<span class="number"> 20</span>  std::map<span class="k3">&lt;</span>Tex, <a href="http://www.allegro.cc/manual/ALLEGRO_BITMAP"><span class="a">ALLEGRO_BITMAP</span></a> <span class="k3">*</span><span class="k3">&gt;</span> textures<span class="k2">;</span>
<span class="number"> 21</span>    
<span class="number"> 22</span>  <span class="k1">static</span> AssetManager instance<span class="k2">;</span>
<span class="number"> 23</span>
<span class="number"> 24</span>public:
<span class="number"> 25</span>  ~AssetManager<span class="k2">(</span><span class="k2">)</span><span class="k2">;</span>
<span class="number"> 26</span>  <span class="k1">static</span> AssetManager <span class="k3">&amp;</span>Instance<span class="k2">(</span><span class="k2">)</span><span class="k2">;</span>
<span class="number"> 27</span>  <span class="k1">void</span> <a href="http://www.allegro.cc/manual/load_bitmap"><span class="a">load_bitmap</span></a><span class="k2">(</span><span class="k1">const</span> Tex <span class="k3">&amp;</span>texName, <span class="k1">const</span> <span class="k1">char</span> <span class="k3">*</span>filename<span class="k2">)</span><span class="k2">;</span>
<span class="number"> 28</span>  <span class="k1">static</span> <a href="http://www.allegro.cc/manual/ALLEGRO_BITMAP"><span class="a">ALLEGRO_BITMAP</span></a><span class="k3">*</span> get_image<span class="k2">(</span><span class="k1">const</span> Tex <span class="k3">&amp;</span>texName<span class="k2">)</span><span class="k2">;</span>
<span class="number"> 29</span>  <span class="k1">void</span> remove_tex<span class="k2">(</span>Tex tex<span class="k2">)</span><span class="k2">;</span>
<span class="number"> 30</span><span class="k2">}</span><span class="k2">;</span>
</div></div><p>
AssetManager&#39;s .cpp file
</p><div class="source-code"><div class="toolbar"><span class="button numbers"><b>#</b></span><span class="button select">Select</span><span class="button expand">Expand</span></div><div class="inner"><span class="number">  1</span><span class="p">#include &lt;allegro5/allegro.h&gt;</span>
<span class="number">  2</span><span class="p">#include &lt;cassert&gt;</span>
<span class="number">  3</span><span class="p">#include "asset_manager.h"</span>
<span class="number">  4</span>
<span class="number">  5</span>
<span class="number">  6</span>AssetManager AssetManager::instance<span class="k2">;</span>
<span class="number">  7</span>
<span class="number">  8</span>AssetManager::~AssetManager<span class="k2">(</span><span class="k2">)</span>
<span class="number">  9</span><span class="k2">{</span>
<span class="number"> 10</span>  std::map<span class="k3">&lt;</span>Tex, <a href="http://www.allegro.cc/manual/ALLEGRO_BITMAP"><span class="a">ALLEGRO_BITMAP</span></a> <span class="k3">*</span><span class="k3">&gt;</span><span class="k2">:</span><span class="k2">:</span>iterator it<span class="k2">;</span>
<span class="number"> 11</span>  <span class="k1">for</span> <span class="k2">(</span>it <span class="k3">=</span> textures.begin<span class="k2">(</span><span class="k2">)</span><span class="k2">;</span> it <span class="k3">!</span><span class="k3">=</span> textures.end<span class="k2">(</span><span class="k2">)</span><span class="k2">;</span> it<span class="k3">+</span><span class="k3">+</span><span class="k2">)</span>
<span class="number"> 12</span>  <span class="k2">{</span>
<span class="number"> 13</span>    <span class="k1">delete</span> it-&gt;second<span class="k2">;</span>
<span class="number"> 14</span>    it-&gt;second <span class="k3">=</span> nullptr<span class="k2">;</span>
<span class="number"> 15</span>  <span class="k2">}</span>
<span class="number"> 16</span>
<span class="number"> 17</span>  textures.clear<span class="k2">(</span><span class="k2">)</span><span class="k2">;</span>
<span class="number"> 18</span>  
<span class="number"> 19</span><span class="k2">}</span>
<span class="number"> 20</span>
<span class="number"> 21</span>AssetManager <span class="k3">&amp;</span>AssetManager::Instance<span class="k2">(</span><span class="k2">)</span>
<span class="number"> 22</span><span class="k2">{</span>
<span class="number"> 23</span>  <span class="k1">return</span> instance<span class="k2">;</span>
<span class="number"> 24</span><span class="k2">}</span>
<span class="number"> 25</span>
<span class="number"> 26</span><span class="k1">void</span> AssetManager::load_bitmap<span class="k2">(</span><span class="k1">const</span> Tex <span class="k3">&amp;</span>texName, <span class="k1">const</span> <span class="k1">char</span> <span class="k3">*</span>filename<span class="k2">)</span>
<span class="number"> 27</span><span class="k2">{</span>
<span class="number"> 28</span>  <a href="http://www.allegro.cc/manual/ALLEGRO_BITMAP"><span class="a">ALLEGRO_BITMAP</span></a> <span class="k3">*</span>bmp<span class="k2">;</span>
<span class="number"> 29</span>  bmp <span class="k3">=</span> <a href="http://www.allegro.cc/manual/al_load_bitmap"><span class="a">al_load_bitmap</span></a><span class="k2">(</span>filename<span class="k2">)</span><span class="k2">;</span>
<span class="number"> 30</span>  <a href="http://www.delorie.com/djgpp/doc/libc/libc_48.html" target="_blank">assert</a><span class="k2">(</span>bmp<span class="k2">)</span><span class="k2">;</span>
<span class="number"> 31</span>  <a href="http://www.allegro.cc/manual/al_convert_mask_to_alpha"><span class="a">al_convert_mask_to_alpha</span></a><span class="k2">(</span>bmp, <a href="http://www.allegro.cc/manual/al_map_rgb"><span class="a">al_map_rgb</span></a><span class="k2">(</span><span class="n">255</span>, <span class="n">0</span>, <span class="n">255</span><span class="k2">)</span><span class="k2">)</span><span class="k2">;</span>
<span class="number"> 32</span>  textures<span class="k2">[</span>texName<span class="k2">]</span> <span class="k3">=</span> bmp<span class="k2">;</span>
<span class="number"> 33</span><span class="k2">}</span>
<span class="number"> 34</span>
<span class="number"> 35</span><a href="http://www.allegro.cc/manual/ALLEGRO_BITMAP"><span class="a">ALLEGRO_BITMAP</span></a><span class="k3">*</span> AssetManager::get_image<span class="k2">(</span><span class="k1">const</span> Tex <span class="k3">&amp;</span>texName<span class="k2">)</span>
<span class="number"> 36</span><span class="k2">{</span>
<span class="number"> 37</span>  <span class="k1">return</span> instance.textures.at<span class="k2">(</span>texName<span class="k2">)</span><span class="k2">;</span>
<span class="number"> 38</span><span class="k2">}</span>
<span class="number"> 39</span>
<span class="number"> 40</span><span class="k1">void</span> AssetManager::remove_tex<span class="k2">(</span>Tex tex<span class="k2">)</span>
<span class="number"> 41</span><span class="k2">{</span>
<span class="number"> 42</span>  std::map<span class="k3">&lt;</span>Tex, <a href="http://www.allegro.cc/manual/ALLEGRO_BITMAP"><span class="a">ALLEGRO_BITMAP</span></a> <span class="k3">*</span><span class="k3">&gt;</span><span class="k2">:</span><span class="k2">:</span>iterator it <span class="k3">=</span> textures.find<span class="k2">(</span>tex<span class="k2">)</span><span class="k2">;</span>
<span class="number"> 43</span>  <span class="k1">if</span> <span class="k2">(</span>it <span class="k3">!</span><span class="k3">=</span> textures.end<span class="k2">(</span><span class="k2">)</span><span class="k2">)</span>
<span class="number"> 44</span>  <span class="k2">{</span>
<span class="number"> 45</span>    <span class="k1">delete</span> it-&gt;second<span class="k2">;</span>
<span class="number"> 46</span>    textures.erase<span class="k2">(</span>it<span class="k2">)</span><span class="k2">;</span>
<span class="number"> 47</span>  <span class="k2">}</span>
<span class="number"> 48</span><span class="k2">}</span>
</div></div><p>
</p></div>]]>
		</description>
		<author>no-reply@allegro.cc (Ojars_L)</author>
		<pubDate>Sun, 21 Feb 2016 01:53:24 +0000</pubDate>
	</item>
	<item>
		<description><![CDATA[<div class="mockup v2"><p>Instead of calling <span class="source-code"><span class="k1">operator</span> <span class="k1">delete</span></span>, which is supposed to correspond to <span class="source-code"><span class="k1">operator</span> <span class="k1">new</span></span>, you need to call <span class="source-code"><a href="http://www.allegro.cc/manual/al_destroy_bitmap"><span class="a">al_destroy_bitmap</span></a><span class="k2">(</span><span class="k2">)</span></span> which will internally <span class="source-code"><a href="http://www.delorie.com/djgpp/doc/libc/libc_350.html" target="_blank">free</a><span class="k2">(</span><span class="k2">)</span></span> all of the <span class="source-code"><a href="http://www.delorie.com/djgpp/doc/libc/libc_551.html" target="_blank">malloc</a><span class="k2">(</span><span class="k2">)</span><span class="k3">-</span>family</span> allocations. In C you use <span class="source-code"><a href="http://www.delorie.com/djgpp/doc/libc/libc_551.html" target="_blank">malloc</a></span> and family to allocate memory on the heap and <span class="source-code"><a href="http://www.delorie.com/djgpp/doc/libc/libc_350.html" target="_blank">free</a></span> to release it. In C++ you use <span class="source-code"><span class="k1">operator</span> <span class="k1">new</span></span> to allocate an object (or primitive) on the heap in the same way and invoke its constructor and you use <span class="source-code"><span class="k1">operator</span> <span class="k1">delete</span></span> to call the destructor and release the memory. You cannot mix them up.
</p></div>]]>
		</description>
		<author>no-reply@allegro.cc (bamccaig)</author>
		<pubDate>Sun, 21 Feb 2016 01:58:27 +0000</pubDate>
	</item>
	<item>
		<description><![CDATA[<div class="mockup v2"><p>Thank&#39;s for so quick answer. I feel foolish... to forget so simple things...<br />This, of course works, bat there is new problem: when I close application, there is an error window saying: game.exe has stopped working. In the &quot;Wiew problem details&quot;:   Fault Module Name:	allegro_monolith-debug-5.1.dll.</p><p>With no AssetManager app closes fine.</p><p>Where could be the problem?
</p></div>]]>
		</description>
		<author>no-reply@allegro.cc (Ojars_L)</author>
		<pubDate>Sun, 21 Feb 2016 02:19:21 +0000</pubDate>
	</item>
	<item>
		<description><![CDATA[<div class="mockup v2"><p>The problem is probably using a global instance and attempting to use the destructor to clean up the objects. Allegro installs an <span class="source-code"><a href="http://www.delorie.com/djgpp/doc/libc/libc_52.html" target="_blank">atexit</a></span> handler that shuts Allegro down, and this is likely happening before C++ gets around to calling your destructor. So Allegro is crashing because it&#39;s no longer in a functioning state. You can try a few things:</p><ul><li><p>Use <span class="source-code"><a href="http://www.allegro.cc/manual/al_install_system"><span class="a">al_install_system</span></a></span> instead of <span class="source-code"><a href="http://www.allegro.cc/manual/al_init"><span class="a">al_init</span></a></span> to initialize Allegro which gives you control over when the <span class="source-code"><a href="http://www.allegro.cc/manual/al_uninstall_system"><span class="a">al_uninstall_system</span></a></span> is called (but then you should make sure it gets called, even if exceptions are thrown, etc....).</p><br /></li><li><p>Instantiate the AssetManager as a local variable in main and pass it around. (Or as a major hack, make it a local in main, but store a pointer to it in global space...)</p><br /></li><li><p>Move the destructor business into a method that you can call early that will destroy the internal state and mark the asset manager &quot;disposed&quot; so it doesn&#39;t repeat this when the destructor is called (based on .NET&#39;s IDisposable interface). Call this method from the destructor, and then call this method before main exits to make sure it happens before Allegro is deinitialized. Example:</p></li></ul><div class="source-code"><div class="toolbar"><span class="button numbers"><b>#</b></span><span class="button select">Select</span><span class="button expand">Expand</span></div><div class="inner"><span class="number">  1</span><span class="k1">void</span> AssetManager::dispose<span class="k2">(</span><span class="k1">void</span><span class="k2">)</span>
<span class="number">  2</span><span class="k2">{</span>
<div class="highlight"><span class="number">  3</span>  <span class="k1">if</span><span class="k2">(</span>this-&gt;disposed<span class="k2">)</span> <span class="k1">return</span><span class="k2">;</span> </div><span class="number">  4</span>
<span class="number">  5</span>  std::map<span class="k3">&lt;</span>Tex, <a href="http://www.allegro.cc/manual/ALLEGRO_BITMAP"><span class="a">ALLEGRO_BITMAP</span></a> <span class="k3">*</span><span class="k3">&gt;</span><span class="k2">:</span><span class="k2">:</span>iterator it<span class="k2">;</span>
<span class="number">  6</span>
<span class="number">  7</span>  <span class="k1">for</span> <span class="k2">(</span>it <span class="k3">=</span> textures.begin<span class="k2">(</span><span class="k2">)</span><span class="k2">;</span> it <span class="k3">!</span><span class="k3">=</span> textures.end<span class="k2">(</span><span class="k2">)</span><span class="k2">;</span> it<span class="k3">+</span><span class="k3">+</span><span class="k2">)</span>
<span class="number">  8</span>  <span class="k2">{</span>
<span class="number">  9</span>    <a href="http://www.allegro.cc/manual/al_destroy_bitmap"><span class="a">al_destroy_bitmap</span></a><span class="k2">(</span>it-&gt;second<span class="k2">)</span><span class="k2">;</span>
<span class="number"> 10</span>    it-&gt;second <span class="k3">=</span> nullptr<span class="k2">;</span>
<span class="number"> 11</span>  <span class="k2">}</span>
<span class="number"> 12</span>
<span class="number"> 13</span>  textures.clear<span class="k2">(</span><span class="k2">)</span><span class="k2">;</span>
<div class="highlight"><span class="number"> 14</span>  this-&gt;disposed <span class="k3">=</span> <span class="k1">true</span><span class="k2">;</span> </div><span class="number"> 15</span><span class="k2">}</span>
</div></div><p>

To be safe you could guard the rest of the methods to refuse to do anything if the object is disposed. Or you could just document that using the object after it has been disposed is undefined/bad and don&#39;t do that.
</p></div>]]>
		</description>
		<author>no-reply@allegro.cc (bamccaig)</author>
		<pubDate>Sun, 21 Feb 2016 02:31:52 +0000</pubDate>
	</item>
	<item>
		<description><![CDATA[<div class="mockup v2"><p>Thank you for advices.<br />I did put code from AssetManager&#39;s destructor to main function before exit and all is OK.
</p></div>]]>
		</description>
		<author>no-reply@allegro.cc (Ojars_L)</author>
		<pubDate>Sun, 21 Feb 2016 12:50:15 +0000</pubDate>
	</item>
</rss>
