title: Undefined reference to new operator
body: <p>Never seen this linker error in my life until I started programming PSP homebrew applications. Anyway, I am making an allegro game and I need to fire projectiles or missiles in this case and I need to use a dynamic and generic array. But my linker complains that there is an undefined reference to the new operator. Below will be the whole source code, makefile, and error details. </p>
  
  <p><strong>Error Details:</strong></p>
  
  <pre><code>1&gt;------ Build started: Project: PSP Asteroids, Configuration: Debug Win32 ------
  1&gt;  psp-g++ -I. -IC:/pspsdk/psp/sdk/include -O2 -G0 -Wall -I. -IC:/pspsdk/psp/sdk/include -O2 -G0 -Wall -fno-exceptions -fno-rtti -D_PSP_FW_VERSION=150   -c -o main.o main.cpp
  1&gt;  psp-gcc -I. -IC:/pspsdk/psp/sdk/include -O2 -G0 -Wall -D_PSP_FW_VERSION=150  -L. -LC:/pspsdk/psp/sdk/lib   main.o -lalleg -lpspgu -lpspirkeyb -lm -lpsppower -lpspaudio -lpsprtc  -lpspdebug -lpspdisplay -lpspge -lpspctrl -lpspsdk -lc -lpspnet -lpspnet_inet -lpspnet_apctl -lpspnet_resolver -lpsputility -lpspuser -lpspkernel -o main.elf
  1&gt;  main.o: In function `std::vector&lt;Missile*, std::allocator&lt;Missile*&gt; &gt;::_M_insert_aux(__gnu_cxx::__normal_iterator&lt;Missile**, std::vector&lt;Missile*, std::allocator&lt;Missile*&gt; &gt; &gt;, Missile* const&amp;)':
  1&gt;  main.cpp:(.text._ZNSt6vectorIP7MissileSaIS1_EE13_M_insert_auxEN9__gnu_cxx17__normal_iteratorIPS1_S3_EERKS1_[_ZNSt6vectorIP7MissileSaIS1_EE13_M_insert_auxEN9__gnu_cxx17__normal_iteratorIPS1_S3_EERKS1_]+0xb8): undefined reference to `operator new(unsigned int)'
  1&gt;  main.cpp:(.text._ZNSt6vectorIP7MissileSaIS1_EE13_M_insert_auxEN9__gnu_cxx17__normal_iteratorIPS1_S3_EERKS1_[_ZNSt6vectorIP7MissileSaIS1_EE13_M_insert_auxEN9__gnu_cxx17__normal_iteratorIPS1_S3_EERKS1_]+0x124): undefined reference to `operator delete(void*)'
  1&gt;  C:\pspsdk\bin\make: *** [main.elf] Error 1
  ========== Build: 1 succeeded, 0 failed, 0 up-to-date, 0 skipped ==========
  </code></pre>
  
  <p><strong>Makefile</strong></p>
  
  <pre><code>TARGET = main
  OBJS = main.o
  
  CFLAGS = -O2 -G0 -Wall
  CXXFLAGS = $(CFLAGS) -fno-exceptions -fno-rtti
  ASFLAGS = $(CFLAGS)
  
  EXTRA_TARGETS = EBOOT.PBP
  PSP_EBOOT_TITLE = PSP Asteroids
  LIBS = -lalleg -lpspgu -lpspirkeyb -lm -lpsppower -lpspaudio -lpsprtc 
  PSPSDK=$(shell psp-config --pspsdk-path)
  include $(PSPSDK)/lib/build.mak 
  </code></pre>
  
  <p><strong>main.cpp</strong></p>
  
  <pre><code>#define ALLEGRO_NO_MAGIC_MAIN
  #define WIDTH 480
  #define HEIGHT 272
  #include &lt;pspkernel.h&gt;
  #include &lt;pspdebug.h&gt;
  #include &lt;pspctrl.h&gt;
  #include &lt;allegro.h&gt;
  #include &lt;math.h&gt;
  #include &lt;vector&gt;
  PSP_MODULE_INFO("PSP Asteroids", 0, 1, 1);
  int check_bb_collision ( BITMAP* spr1, BITMAP* spr2, int x1, int y1, int x2, int y2)
  {
      int b1_x = x1;
      int b2_x = x2;
      int b1_y = y1;
      int b2_y = y2;
      int b1_w = spr1-&gt;w;
      int b2_w = spr2-&gt;w;
      int b1_h = spr1-&gt;h;
      int b2_h = spr2-&gt;h;
      if ( ( b1_x &gt; b2_x + b2_w - 1 )  ||  // is b1 on the right side of b2?
                  ( b1_y &gt; b2_y + b2_h - 1 )       ||  // is b1 under b2?
                  ( b2_x &gt; b1_x + b1_w - 1 )       ||  // is b2 on the right side of b1?
                  ( b2_y &gt; b1_y + b1_h - 1 ) )         // is b2 under b1?
      {
          // no collision
          return 0;
      }
  
      // collision
      return 1;
  }
  //Pass 2 Allegro bitmaps and their respective positions and this function
  //returns true if there is a collision and false if theres not.
  //The 2 bitmaps must be memory bitmaps of the same color depth.
  int check_pp_collision_normal(BITMAP *spr1, BITMAP *spr2, int x1, int y1, int x2, int y2)
  {
   int dx1, dx2, dy1, dy2; //We will use this deltas...
   int fx,fy,sx1,sx2; //Also we will use this starting/final position variables...
   int maxw, maxh; //And also this variables saying what is the maximum width and height...
   int depth; //This will store the color depth value...
   char CHARVAR; //We will use these to store the transparent color for the sprites...
   short SHORTVAR;
   long LONGVAR;
  
   if( !check_bb_collision(spr1, spr2, x1,y1, x2,y2) ) return 0; //If theres not a bounding box collision, it is impossible to have a pixel perfect collision right? So, we return that theres not collision...
  
   //First we need to see how much we have to shift the coordinates of the sprites...
   if(x1&gt;x2) {
     dx1=0;      //don't need to shift sprite 1.
     dx2=x1-x2;  //shift sprite 2 left. Why left? Because we have the sprite 1 being on the right of the sprite 2, so we have to move sprite 2 to the left to do the proper pixel perfect collision...
     } else {
     dx1=x2-x1;  //shift sprite 1 left.
     dx2=0;      //don't need to shift sprite 2.
     }
   if(y1&gt;y2) {
     dy1=0;
     dy2=y1-y2;  //we need to move this many rows up sprite 2. Why up? Because we have sprite 1 being down of sprite 2, so we have to move sprite 2 up to do the proper pixel perfect collision detection...
     } else {
     dy1=y2-y1;  //we need to move this many rows up sprite 1.
     dy2=0;
     }
  
   //Then, we have to see how far we have to go, we do this seeing the minimum height and width between the 2 sprites depending in their positions:
   if(spr1-&gt;w-dx1 &gt; spr2-&gt;w-dx2) {
     maxw=spr2-&gt;w-dx2;
     } else {
     maxw=spr1-&gt;w-dx1;
     }
   if(spr1-&gt;h-dy1 &gt; spr2-&gt;h-dy2) {
     maxh=spr2-&gt;h-dy2;
     } else {
     maxh=spr1-&gt;h-dy1;
     }
   maxw--;
   maxh--;
  
   fy=dy1;
   fx=dx1;
   dy1+=maxh;
   dy2+=maxh;
   sx1=dx1+maxw;
   sx2=dx2+maxw;
  
   depth=bitmap_color_depth(spr1); //Get the bitmap depth...
  
   if(depth==8) {
     CHARVAR=bitmap_mask_color(spr1); //Get the transparent color of the sprites...
     for(; dy1&gt;=fy; dy1--,dy2--) { //Go through lines...
        for(dx1=sx1,dx2=sx2; dx1&gt;=fx; dx1--,dx2--) { //Go through the X axis...
           if((spr1-&gt;line[dy1][dx1]!=CHARVAR) &amp;&amp; (spr2-&gt;line[dy2][dx2]!=CHARVAR)) return 1; //Both sprites don't have transparent color in that position, so, theres a collision and return collision detected!
           }
        }
     } else {
     if(depth==16 || depth==15) {
       SHORTVAR=bitmap_mask_color(spr1); //Get the transparent color of the sprites...
       for(; dy1&gt;=fy; dy1--,dy2--) { //Go through lines...
          for(dx1=sx1,dx2=sx2; dx1&gt;=fx; dx1--,dx2--) { //Go through the X axis...
             if(( ((short *)spr1-&gt;line[dy1])[dx1]!=SHORTVAR) &amp;&amp; ( ((short *)spr2-&gt;line[dy2])[dx2]!=SHORTVAR)) return 1; //Both sprites don't have transparent color in that position, so, theres a collision and return collision detected!
             }
          }
       } else {
       if(depth==32) {
         LONGVAR=bitmap_mask_color(spr1); //Get the transparent color of the sprites...
         for(; dy1&gt;=fy; dy1--,dy2--) { //Go through lines...
            for(dx1=sx1,dx2=sx2; dx1&gt;=fx; dx1--,dx2--) { //Go through the X axis...
               if(( ((long *)spr1-&gt;line[dy1])[dx1]!=LONGVAR) &amp;&amp; ( ((long *)spr2-&gt;line[dy2])[dx2]!=LONGVAR)) return 1; //Both sprites don't have transparent color in that position, so, theres a collision and return collision detected!
               }
            }
         } else {
         if(depth==24) {
           CHARVAR=bitmap_mask_color(spr1)&gt;&gt;16; //if the order is RGB, this will contain B...
           SHORTVAR=bitmap_mask_color(spr1)&amp;0xffff; //if the order is RGB, this will contain GR...
           for(; dy1&gt;=fy; dy1--,dy2--) { //Go through lines...
              for(dx1=sx1,dx2=sx2; dx1&gt;=fx; dx1--,dx2--) { //Go through the X axis...
                 if( (*((short *)(spr1-&gt;line[dy1]+(dx1)*3))!=SHORTVAR) &amp;&amp; (spr1-&gt;line[dy1][(dx1)*3+2]!=CHARVAR)  &amp;&amp;  (*((short *)(spr2-&gt;line[dy2]+(dx2)*3))!=SHORTVAR) &amp;&amp; (spr2-&gt;line[dy2][(dx2)*3+2]!=CHARVAR) ) return 1; //Both sprites don't have transparent color in that position, so, theres a collision and return collision detected!
                 //I have tryed to avoid the above multiplications but it seems that GCC optimizes better than I :-))
                 }
              }
           }
         }
       }
     }
  
   //If we have reached here it means that theres not a collision:
   return 0; //Return no collision.
   }
  //Finds the magnitude from a point in 2d.
  double magnitude(int x, int y)
  {
  
      return sqrt((x * x) + (y* y));
  }
  char* itoa(int val, int base){
  
      static char buf[32] = {0};
  
      int i = 30;
  
      for(; val &amp;&amp; i ; --i, val /= base)
  
          buf[i] = "0123456789abcdef"[val % base];
  
      return &amp;buf[i+1];
  
  }
  // static class that contain special game constants
  class Constants
  {
      public:
          static const double PI = 3.14159265358979323846;
          static const double PIOVER4 = (3.14159265358979323846 / 4);
          static const double TWOPI = (2 * 3.14159265358979323846);
          static const double PIOVER2 = (3.14159265358979323846 / 2);
          static const unsigned int MAXBULLETS = 5;
  };
  // Clamp
  inline float clamp(float x, float min, float max)
  {
      return x &lt; min ? min : (x &gt; max ? max : x);
  }
  // The ship class
  class Ship
  {
      public:
          double X;
          static const double Y = (272 - 64);
          double angle;
          void Init(int x)
          {
  
              angle = 0;
              X = x;
          }
          void MoveLeft()
          {
              X -= 2;
  
          }
          void MoveRight()
          {
              X += 2;
          }
  
          void Draw(BITMAP* buffer, BITMAP* sprite, int frame)
          {
              X = clamp(X, 0, 480);
              draw_sprite(buffer, sprite, X, Y);
          }
  };
  class Missile
  {
      private:
          static const double angle = (3.14159265358979323846 / 2);
      public:
          bool Alive;
          static const int V = 5;
          double X;
          double Y;
          void Init(bool alive, int x, int y)
          {
              Alive = alive;
              X = x;
              Y = y;
          }
          void Update()
          {
              X += V * cos(angle);
              Y += V * sin(angle);
          }
          void Kill()
          {
              Alive = false;
          }
          void Draw(BITMAP* buffer, BITMAP* sprite)
          {
              draw_sprite(buffer, sprite, X, Y);
          }
  };
  std::vector&lt;Missile*&gt;* bullets = (std::vector&lt;Missile*&gt;*)malloc(1);
  void FireBullet(Ship* s)
  {
      if (bullets-&gt;size() &lt; Constants::MAXBULLETS)
      {
          Missile* missile = (Missile*)malloc(1);
          missile-&gt;Init(true, s-&gt;X, s-&gt;Y);
          bullets-&gt;push_back(missile);
      }
  }
  
  void CleanUp()
  {
      for(unsigned int index = 0; index &lt; bullets-&gt;size(); index++)
      {
  
          if (bullets-&gt;at(index)-&gt;Alive == false)
          {
              bullets-&gt;erase(bullets-&gt;begin() + index);
          }
      }
  }
  void UpdateBullets()
  {
      for(unsigned int index = 0; index &lt; bullets-&gt;size(); index++)
      {
          if (bullets-&gt;at(index)-&gt;Y &lt; 0)
          {
              bullets-&gt;at(index)-&gt;Update();
          }
          else
          {
              bullets-&gt;at(index)-&gt;Kill();
          }
      }
  }
  void DrawBullets(BITMAP* buffer, BITMAP* sprite)
  {
      for(unsigned int index = 0; index &lt; bullets-&gt;size(); index++)
      {
          if (bullets-&gt;at(index)-&gt;Alive == true)
          {
              bullets-&gt;at(index)-&gt;Draw(buffer, sprite);
          }
      }
  }
  //Entry point of the application
  int main(void)
  {   
  
      Ship* s = (Ship*)malloc(1);
      int x = (WIDTH / 2) - 64;
      allegro_message("Initialzing ship class");
      s-&gt;Init(x);
      int frame = 0;
      BITMAP* buffer = NULL;
      BITMAP* background = NULL;
      BITMAP* ship = NULL;
      SceCtrlData pad;
      bool done = false;
      allegro_message("Initializing Game...");
      int rval = allegro_init();
      if (allegro_init() != 0)
      {
          allegro_message("Error initializing Game Because it returned: %i", rval);
          return 1;
      }
      allegro_message("Setting Graphics Mode...Press X To Begin Game");
      set_color_depth(32);
      int ret = set_gfx_mode(GFX_AUTODETECT,480,272,0,0);
      if (ret != 0)
      {
          allegro_message("Error setting grahpic mode! Because of it returned: %i", ret);
          return ret;
      }
      background = load_bmp("background.bmp", NULL);
      ship = load_bmp("ship.bmp", NULL);
      BITMAP* m = load_bmp("missile.bmp", NULL);
      if (background == NULL || ship == NULL || m != NULL){
          allegro_message("Couldn't load one or more sprites...");
          return 0;
      }
      buffer = create_bitmap(WIDTH, HEIGHT);
      if (buffer == NULL)
      {
          allegro_message("Couldn't create buffer!");
          return 0;
      }
      int previousx = 0;
      int previousy = 0;
      while(!done)
      {
  
          sceCtrlReadBufferPositive(&amp;pad, 1); 
          if (pad.Buttons &amp; PSP_CTRL_START)
          {
              done = true;
          }
          else if (pad.Buttons &amp; PSP_CTRL_CROSS)
          {
              FireBullet(s);
          }
          else if (pad.Buttons &amp; PSP_CTRL_LEFT)
          {
              s-&gt;MoveLeft();
          }
          else if (pad.Buttons &amp; PSP_CTRL_RIGHT)
          {
              s-&gt;MoveRight();
          }
          UpdateBullets();
          CleanUp();
          clear(buffer);
          draw_sprite(buffer, background, 0, 0);
          s-&gt;Draw(buffer, ship, frame);
          DrawBullets(buffer, ship);
          masked_blit(buffer, screen, 0, 0, 0, 0, WIDTH, HEIGHT);
          if (frame == (60 * 10))
          {
              frame = 0;
          }
          frame++;
          vsync();
          previousx = pad.Lx;
          previousy = pad.Ly;
  
      }
      allegro_message("Clearing resources!");
      clear(buffer);  
      clear(ship);
      clear(background);
      clear(screen);
      allegro_message("Thank you for playing!");
      return 0;
  }
  END_OF_MAIN()
  </code></pre>
  
  <p>If this error cannot be fixed is there a  work around. Like what can I use that doesn't use the new operator. I mean I use malloc for dynamically allocating everything but the vector template class is somehow using the new operator.</p>