Subversion Repositories Kolibri OS

Rev

Blame | Last modification | View Log | RSS feed

  1. // -*- C++ -*-
  2. //
  3. // Copyright (C) 2009-2013 Free Software Foundation, Inc.
  4. //
  5. // This file is part of the GNU ISO C++ Library.  This library is free
  6. // software; you can redistribute it and/or modify it under the
  7. // terms of the GNU General Public License as published by the
  8. // Free Software Foundation; either version 3, or (at your option)
  9. // any later version.
  10. //
  11. // This library is distributed in the hope that it will be useful,
  12. // but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  14. // GNU General Public License for more details.
  15.  
  16. // Under Section 7 of GPL version 3, you are granted additional
  17. // permissions described in the GCC Runtime Library Exception, version
  18. // 3.1, as published by the Free Software Foundation.
  19.  
  20. // You should have received a copy of the GNU General Public License along
  21. // with this library; see the file COPYING3.  If not see
  22. // <http://www.gnu.org/licenses/>.
  23.  
  24. /** @file profile/impl/profiler_map_to_unordered_map.h
  25.  *  @brief Diagnostics for map to unordered_map.
  26.  */
  27.  
  28. // Written by Silvius Rus.
  29.  
  30. #ifndef _GLIBCXX_PROFILE_PROFILER_MAP_TO_UNORDERED_MAP_H
  31. #define _GLIBCXX_PROFILE_PROFILER_MAP_TO_UNORDERED_MAP_H 1
  32.  
  33. #include "profile/impl/profiler.h"
  34. #include "profile/impl/profiler_node.h"
  35. #include "profile/impl/profiler_trace.h"
  36.  
  37. namespace __gnu_profile
  38. {
  39.   inline int
  40.   __log2(std::size_t __size)
  41.   {
  42.     for (int __bit_count = sizeof(std::size_t) - 1; __bit_count >= 0;
  43.          -- __bit_count)
  44.       if ((2 << __bit_count) & __size)
  45.         return __bit_count;
  46.     return 0;
  47.   }
  48.  
  49.   inline float
  50.   __map_insert_cost(std::size_t __size)
  51.   { return (_GLIBCXX_PROFILE_DATA(__map_insert_cost_factor).__value
  52.             * static_cast<float>(__log2(__size))); }
  53.  
  54.   inline float
  55.   __map_erase_cost(std::size_t __size)
  56.   { return (_GLIBCXX_PROFILE_DATA(__map_erase_cost_factor).__value
  57.             * static_cast<float>(__log2(__size))); }
  58.  
  59.   inline float
  60.   __map_find_cost(std::size_t __size)
  61.   { return (_GLIBCXX_PROFILE_DATA(__map_find_cost_factor).__value
  62.             * static_cast<float>(__log2(__size))); }
  63.  
  64.   /** @brief A map-to-unordered_map instrumentation line in the
  65.       object table.  */
  66.   class __map2umap_info
  67.   : public __object_info_base
  68.   {
  69.   public:
  70.     __map2umap_info()
  71.     : _M_insert(0), _M_erase(0), _M_find(0), _M_iterate(0),
  72.       _M_umap_cost(0.0), _M_map_cost(0.0), _M_valid(true) { }
  73.    
  74.     __map2umap_info(__stack_t __stack)
  75.     : __object_info_base(__stack), _M_insert(0), _M_erase(0), _M_find(0),
  76.       _M_iterate(0), _M_umap_cost(0.0), _M_map_cost(0.0), _M_valid(true) { }
  77.  
  78.     virtual ~__map2umap_info() { }
  79.  
  80.     __map2umap_info(const __map2umap_info& __o)
  81.     : __object_info_base(__o), _M_insert(__o._M_insert),
  82.       _M_erase(__o._M_erase), _M_find(__o._M_find),
  83.       _M_iterate(__o._M_iterate), _M_umap_cost(__o._M_umap_cost),
  84.       _M_map_cost(__o._M_map_cost), _M_valid(__o._M_valid) { }
  85.  
  86.     void
  87.     __merge(const __map2umap_info& __o)
  88.     {
  89.       _M_insert    += __o._M_insert;
  90.       _M_erase     += __o._M_erase;
  91.       _M_find      += __o._M_find;
  92.       _M_umap_cost += __o._M_umap_cost;
  93.       _M_map_cost  += __o._M_map_cost;
  94.       _M_valid     &= __o._M_valid;
  95.     }
  96.  
  97.     void
  98.     __write(FILE* __f) const
  99.     {
  100.       std::fprintf(__f, "%Zu %Zu %Zu %Zu %.0f %.0f %s\n",
  101.                    _M_insert, _M_erase, _M_find, _M_iterate, _M_map_cost,
  102.                    _M_umap_cost, _M_valid ? "valid" : "invalid");
  103.     }
  104.  
  105.     float
  106.     __magnitude() const
  107.     { return _M_map_cost - _M_umap_cost; }
  108.  
  109.     std::string
  110.     __advice() const
  111.     { return "change std::map to std::unordered_map"; }
  112.  
  113.     void
  114.     __record_insert(std::size_t __size, std::size_t __count)
  115.     {
  116.       _M_insert += __count;
  117.       _M_map_cost += __count * __map_insert_cost(__size);
  118.       _M_umap_cost
  119.         += (__count
  120.             * _GLIBCXX_PROFILE_DATA(__umap_insert_cost_factor).__value);
  121.     }
  122.  
  123.     void
  124.     __record_erase(std::size_t __size, std::size_t __count)
  125.     {
  126.       _M_erase += __count;
  127.       _M_map_cost += __count * __map_erase_cost(__size);
  128.       _M_umap_cost
  129.         += (__count
  130.             * _GLIBCXX_PROFILE_DATA(__umap_erase_cost_factor).__value);
  131.     }
  132.  
  133.     void
  134.     __record_find(std::size_t __size)
  135.     {
  136.       _M_find += 1;
  137.       _M_map_cost += __map_find_cost(__size);
  138.       _M_umap_cost += _GLIBCXX_PROFILE_DATA(__umap_find_cost_factor).__value;
  139.     }
  140.  
  141.     void
  142.     __record_iterate(std::size_t __count)
  143.     {
  144.       _M_iterate += __count;
  145.       _M_map_cost
  146.         += (__count
  147.             * _GLIBCXX_PROFILE_DATA(__map_iterate_cost_factor).__value);
  148.       _M_umap_cost
  149.         += (__count
  150.             * _GLIBCXX_PROFILE_DATA(__umap_iterate_cost_factor).__value);
  151.     }
  152.  
  153.     void
  154.     __record_invalidate()
  155.     { _M_valid = false; }
  156.  
  157.   private:
  158.     std::size_t _M_insert;
  159.     std::size_t _M_erase;
  160.     std::size_t _M_find;
  161.     std::size_t _M_iterate;
  162.     float _M_umap_cost;
  163.     float _M_map_cost;
  164.     bool  _M_valid;
  165.   };
  166.  
  167.  
  168.   /** @brief A map-to-unordered_map instrumentation line in the
  169.       stack table.  */
  170.   class __map2umap_stack_info
  171.   : public __map2umap_info
  172.   {
  173.   public:
  174.     __map2umap_stack_info(const __map2umap_info& __o)
  175.     : __map2umap_info(__o) { }
  176.   };
  177.  
  178.   /** @brief Map-to-unordered_map instrumentation producer.  */
  179.   class __trace_map2umap
  180.   : public __trace_base<__map2umap_info, __map2umap_stack_info>
  181.   {
  182.   public:
  183.     __trace_map2umap()
  184.     : __trace_base<__map2umap_info, __map2umap_stack_info>()
  185.     { __id = "map-to-unordered-map"; }
  186.   };
  187.  
  188.   inline void
  189.   __trace_map_to_unordered_map_init()
  190.   { _GLIBCXX_PROFILE_DATA(_S_map2umap) = new __trace_map2umap(); }
  191.  
  192.   inline void
  193.   __trace_map_to_unordered_map_report(FILE* __f,
  194.                                       __warning_vector_t& __warnings)
  195.   {
  196.     if (_GLIBCXX_PROFILE_DATA(_S_map2umap))
  197.       {
  198.         _GLIBCXX_PROFILE_DATA(_S_map2umap)->__collect_warnings(__warnings);
  199.         _GLIBCXX_PROFILE_DATA(_S_map2umap)->__write(__f);
  200.       }
  201.   }
  202.  
  203.   inline void
  204.   __trace_map_to_unordered_map_construct(const void* __obj)
  205.   {
  206.     if (!__profcxx_init())
  207.       return;
  208.  
  209.     _GLIBCXX_PROFILE_DATA(_S_map2umap)->
  210.       __add_object(__obj, __map2umap_info(__get_stack()));
  211.   }
  212.  
  213.   inline void
  214.   __trace_map_to_unordered_map_destruct(const void* __obj)
  215.   {
  216.     if (!__profcxx_init())
  217.       return;
  218.  
  219.     _GLIBCXX_PROFILE_DATA(_S_map2umap)->__retire_object(__obj);
  220.   }
  221.  
  222.   inline void
  223.   __trace_map_to_unordered_map_insert(const void* __obj,
  224.                                       std::size_t __size, std::size_t __count)
  225.   {
  226.     if (!__profcxx_init())
  227.       return;
  228.  
  229.     __map2umap_info* __info
  230.       = _GLIBCXX_PROFILE_DATA(_S_map2umap)->__get_object_info(__obj);
  231.  
  232.     if (__info)
  233.       __info->__record_insert(__size, __count);
  234.   }
  235.  
  236.   inline void
  237.   __trace_map_to_unordered_map_erase(const void* __obj,
  238.                                      std::size_t __size, std::size_t __count)
  239.   {
  240.     if (!__profcxx_init())
  241.       return;
  242.  
  243.     __map2umap_info* __info
  244.       = _GLIBCXX_PROFILE_DATA(_S_map2umap)->__get_object_info(__obj);
  245.  
  246.     if (__info)
  247.       __info->__record_erase(__size, __count);
  248.   }
  249.  
  250.   inline void
  251.   __trace_map_to_unordered_map_find(const void* __obj, std::size_t __size)
  252.   {
  253.     if (!__profcxx_init())
  254.       return;
  255.  
  256.     __map2umap_info* __info
  257.       = _GLIBCXX_PROFILE_DATA(_S_map2umap)->__get_object_info(__obj);
  258.  
  259.     if (__info)
  260.       __info->__record_find(__size);
  261.   }
  262.  
  263.   inline void
  264.   __trace_map_to_unordered_map_iterate(const void* __obj, std::size_t __count)
  265.   {
  266.     if (!__profcxx_init())
  267.       return;
  268.  
  269.     __map2umap_info* __info
  270.       = _GLIBCXX_PROFILE_DATA(_S_map2umap)->__get_object_info(__obj);
  271.    
  272.     if (__info)
  273.       __info->__record_iterate(__count);
  274.   }
  275.  
  276.   inline void
  277.   __trace_map_to_unordered_map_invalidate(const void* __obj)
  278.   {
  279.     if (!__profcxx_init())
  280.       return;
  281.  
  282.     __map2umap_info* __info
  283.       = _GLIBCXX_PROFILE_DATA(_S_map2umap)->__get_object_info(__obj);
  284.  
  285.     if (__info)
  286.       __info->__record_invalidate();
  287.   }
  288.  
  289. } // namespace __gnu_profile
  290. #endif /* _GLIBCXX_PROFILE_PROFILER_MAP_TO_UNORDERED_MAP_H */
  291.