Blame src/memory/SharedPtr.cpp

Packit bfcc33
#include "../sass.hpp"
Packit bfcc33
#include <iostream>
Packit bfcc33
#include <typeinfo>
Packit bfcc33
Packit bfcc33
#include "SharedPtr.hpp"
Packit bfcc33
#include "../ast_fwd_decl.hpp"
Packit bfcc33
Packit bfcc33
#ifdef DEBUG_SHARED_PTR
Packit bfcc33
#include "../debugger.hpp"
Packit bfcc33
#endif
Packit bfcc33
Packit bfcc33
namespace Sass {
Packit bfcc33
Packit bfcc33
  #ifdef DEBUG_SHARED_PTR
Packit bfcc33
  void SharedObj::dumpMemLeaks() {
Packit bfcc33
    if (!all.empty()) {
Packit bfcc33
      std::cerr << "###################################\n";
Packit bfcc33
      std::cerr << "# REPORTING MISSING DEALLOCATIONS #\n";
Packit bfcc33
      std::cerr << "###################################\n";
Packit bfcc33
      for (SharedObj* var : all) {
Packit bfcc33
        if (AST_Node_Ptr ast = dynamic_cast<AST_Node*>(var)) {
Packit bfcc33
          debug_ast(ast);
Packit bfcc33
        } else {
Packit bfcc33
          std::cerr << "LEAKED " << var << "\n";
Packit bfcc33
        }
Packit bfcc33
      }
Packit bfcc33
    }
Packit bfcc33
  }
Packit bfcc33
  std::vector<SharedObj*> SharedObj::all;
Packit bfcc33
  #endif
Packit bfcc33
Packit bfcc33
  bool SharedObj::taint = false;
Packit bfcc33
Packit bfcc33
  SharedObj::SharedObj()
Packit bfcc33
  : detached(false)
Packit bfcc33
    #ifdef DEBUG_SHARED_PTR
Packit bfcc33
    , dbg(false)
Packit bfcc33
    #endif
Packit bfcc33
  {
Packit bfcc33
    refcounter = 0;
Packit bfcc33
    #ifdef DEBUG_SHARED_PTR
Packit bfcc33
      if (taint) all.push_back(this);
Packit bfcc33
    #endif
Packit bfcc33
  };
Packit bfcc33
Packit bfcc33
  SharedObj::~SharedObj() {
Packit bfcc33
    #ifdef DEBUG_SHARED_PTR
Packit bfcc33
      if (dbg) std::cerr << "Destruct " << this << "\n";
Packit bfcc33
      if(!all.empty()) { // check needed for MSVC (no clue why?)
Packit bfcc33
        all.erase(std::remove(all.begin(), all.end(), this), all.end());
Packit bfcc33
      }
Packit bfcc33
    #endif
Packit bfcc33
  };
Packit bfcc33
Packit bfcc33
  void SharedPtr::decRefCount() {
Packit bfcc33
    if (node) {
Packit bfcc33
      -- node->refcounter;
Packit bfcc33
      #ifdef DEBUG_SHARED_PTR
Packit bfcc33
        if (node->dbg)  std::cerr << "- " << node << " X " << node->refcounter << " (" << this << ") " << "\n";
Packit bfcc33
      #endif
Packit bfcc33
      if (node->refcounter == 0) {
Packit bfcc33
        #ifdef DEBUG_SHARED_PTR
Packit bfcc33
          // AST_Node_Ptr ast = dynamic_cast<AST_Node*>(node);
Packit bfcc33
          if (node->dbg) std::cerr << "DELETE NODE " << node << "\n";
Packit bfcc33
        #endif
Packit bfcc33
        if (!node->detached) {
Packit bfcc33
          delete(node);
Packit bfcc33
        }
Packit bfcc33
      }
Packit bfcc33
    }
Packit bfcc33
  }
Packit bfcc33
Packit bfcc33
  void SharedPtr::incRefCount() {
Packit bfcc33
    if (node) {
Packit bfcc33
      ++ node->refcounter;
Packit bfcc33
      node->detached = false;
Packit bfcc33
      #ifdef DEBUG_SHARED_PTR
Packit bfcc33
        if (node->dbg) {
Packit bfcc33
          std::cerr << "+ " << node << " X " << node->refcounter << " (" << this << ") " << "\n";
Packit bfcc33
        }
Packit bfcc33
      #endif
Packit bfcc33
    }
Packit bfcc33
  }
Packit bfcc33
Packit bfcc33
  SharedPtr::~SharedPtr() {
Packit bfcc33
    decRefCount();
Packit bfcc33
  }
Packit bfcc33
Packit bfcc33
Packit bfcc33
  // the create constructor
Packit bfcc33
  SharedPtr::SharedPtr(SharedObj* ptr)
Packit bfcc33
  : node(ptr) {
Packit bfcc33
    incRefCount();
Packit bfcc33
  }
Packit bfcc33
  // copy assignment operator
Packit bfcc33
  SharedPtr& SharedPtr::operator=(const SharedPtr& rhs) {
Packit bfcc33
    void* cur_ptr = (void*) node;
Packit bfcc33
    void* rhs_ptr = (void*) rhs.node;
Packit bfcc33
    if (cur_ptr == rhs_ptr) {
Packit bfcc33
      return *this;
Packit bfcc33
    }
Packit bfcc33
    decRefCount();
Packit bfcc33
    node = rhs.node;
Packit bfcc33
    incRefCount();
Packit bfcc33
    return *this;
Packit bfcc33
  }
Packit bfcc33
Packit bfcc33
  // the copy constructor
Packit bfcc33
  SharedPtr::SharedPtr(const SharedPtr& obj)
Packit bfcc33
  : node(obj.node) {
Packit bfcc33
    incRefCount();
Packit bfcc33
  }
Packit bfcc33
Packit bfcc33
}