1 /*
   2  * Copyright (c) 2014, 2015, Dynatrace and/or its affiliates. All rights reserved.
   3  * 
   4  * This file is part of the Lock Contention Tracing Subsystem for the HotSpot
   5  * Virtual Machine, which is developed at Christian Doppler Laboratory on
   6  * Monitoring and Evolution of Very-Large-Scale Software Systems. Please
   7  * contact us at <http://mevss.jku.at/> if you need additional information
   8  * or have any questions.
   9  *
  10  * This code is free software; you can redistribute it and/or modify it
  11  * under the terms of the GNU General Public License version 2 only, as
  12  * published by the Free Software Foundation.
  13  *
  14  * This code is distributed in the hope that it will be useful, but WITHOUT
  15  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  16  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  17  * version 2 for more details (a copy is included in the LICENSE file that
  18  * accompanied this code).
  19  *
  20  * You should have received a copy of the GNU General Public License version
  21  * 2 along with this work. If not, see <http://www.gnu.org/licenses/>.
  22  *
  23  */ 
  24 package sun.evtracing.processing.statistics;
  25 
  26 import java.util.HashMap;
  27 import java.util.Map;
  28 import java.util.regex.Pattern;
  29 
  30 import sun.evtracing.processing.statistics.aggregator.ContentionProcessor;
  31 import sun.evtracing.processing.statistics.metadata.JavaObject;
  32 import sun.evtracing.processing.statistics.metadata.ParkEventTuple;
  33 
  34 public class ParkBlockerDispatcher implements ParkBlockerAnalyser {
  35         private final ContentionProcessor cproc;
  36         private final ParkBlockerAnalyser nopAnalyser;
  37 
  38         private final Map<JavaObject, ParkBlockerAnalyser> analyser = new HashMap<>();
  39 
  40         public ParkBlockerDispatcher(ContentionProcessor cproc) {
  41                 this(cproc, null);
  42         }
  43 
  44         public ParkBlockerDispatcher(ContentionProcessor cproc, Pattern[] condWaitPatterns) {
  45                 this.cproc = cproc;
  46                 this.nopAnalyser = new ParkBlockerNopAnalyser(cproc, condWaitPatterns);
  47         }
  48 
  49         private ParkBlockerAnalyser getOrCreate(ParkEventTuple tuple) {
  50                 JavaObject blocker = tuple.blocker().top();
  51 
  52                 ParkBlockerAnalyser a = analyser.get(blocker);
  53                 if (a != null) {
  54                         return a;
  55                 }
  56 
  57                 a = create(blocker);
  58                 if (a != null) {
  59                         analyser.put(blocker, a);
  60                         return a;
  61                 }
  62 
  63                 return nopAnalyser;
  64         }
  65 
  66         private ParkBlockerAnalyser create(JavaObject obj) {
  67                 switch (obj.clazz().name()) {
  68                 case "java/util/concurrent/locks/ReentrantLock$FairSync":
  69                 case "java/util/concurrent/locks/ReentrantLock$NonfairSync":
  70                         return new ParkBlockerReentrantLockAnalyser(cproc);
  71                 case "java/util/concurrent/locks/ReentrantReadWriteLock$FairSync":
  72                 case "java/util/concurrent/locks/ReentrantReadWriteLock$NonfairSync":
  73                         return new ParkBlockerReentrantReadWriteLockAnalyser(cproc);
  74                 default:
  75                         return null;
  76                 }
  77         }
  78 
  79         @Override
  80         public void begin(ParkEventTuple tuple) {
  81                 getOrCreate(tuple).begin(tuple);
  82         }
  83 
  84         @Override
  85         public void end(ParkEventTuple tuple) {
  86                 getOrCreate(tuple).end(tuple);
  87         }
  88 
  89         @Override
  90         public void finish(ParkEventTuple tuple) {
  91                 getOrCreate(tuple).finish(tuple);
  92         }
  93 }