Clover Coverage Report
Coverage timestamp: Fri May 24 2013 13:47:27 UTC
../../../../../../img/srcFileCovDistChart7.png 74% of files have more coverage
72   197   20   14.4
26   130   0.28   5
5     4  
1    
 
  KernelQedeqBoStorage       Line # 38 72 20 68.9% 0.6893204
 
  (97)
 
1    /* This file is part of the project "Hilbert II" - http://www.qedeq.org
2    *
3    * Copyright 2000-2013, Michael Meyling <mime@qedeq.org>.
4    *
5    * "Hilbert II" is free software; you can redistribute
6    * it and/or modify it under the terms of the GNU General Public
7    * License as published by the Free Software Foundation; either
8    * version 2 of the License, or (at your option) any later version.
9    *
10    * This program is distributed in the hope that it will be useful,
11    * but WITHOUT ANY WARRANTY; without even the implied warranty of
12    * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13    * GNU General Public License for more details.
14    */
15   
16    package org.qedeq.kernel.bo.service.control;
17   
18    import java.util.ArrayList;
19    import java.util.HashMap;
20    import java.util.Iterator;
21    import java.util.List;
22    import java.util.Map;
23   
24    import org.apache.commons.lang.StringUtils;
25    import org.qedeq.base.trace.Trace;
26    import org.qedeq.kernel.bo.KernelContext;
27    import org.qedeq.kernel.bo.common.QedeqBo;
28    import org.qedeq.kernel.bo.log.QedeqLog;
29    import org.qedeq.kernel.bo.module.InternalKernelServices;
30    import org.qedeq.kernel.bo.module.KernelModuleReferenceList;
31    import org.qedeq.kernel.bo.module.KernelQedeqBo;
32    import org.qedeq.kernel.se.common.ModuleAddress;
33    import org.qedeq.kernel.se.state.LoadingState;
34   
35    /**
36    * Holds all known QEDEQ modules.
37    */
 
38    class KernelQedeqBoStorage {
39   
40    /** This class. */
41    private static final Class CLASS = KernelQedeqBoStorage.class;
42   
43    /** QEDEQ Modules; key: ModuleAddress, value: KernelQedeqBo. */
44    private final Map bos = new HashMap();
45   
46   
47    /**
48    * Get {@link QedeqBo} for an module address. If it is unknown it will be created.
49    *
50    * @param services Internal kernel services.
51    * @param address Module address.
52    * @return QedeqBo for module.
53    */
 
54  45763 toggle synchronized DefaultKernelQedeqBo getKernelQedeqBo(final InternalKernelServices services,
55    final ModuleAddress address) {
56  45763 if (bos.containsKey(address)) {
57  45160 return (DefaultKernelQedeqBo) bos.get(address);
58    }
59  603 final DefaultKernelQedeqBo prop = new DefaultKernelQedeqBo(services, address);
60  603 bos.put(address, prop);
61  603 return prop;
62    }
63   
64    /**
65    * Remove all modules from memory.
66    */
 
67  471 toggle synchronized void removeAllModules() {
68  471 final String method = "removeAllModules()";
69  471 Trace.begin(CLASS, this, method);
70  471 try {
71  471 for (final Iterator iterator
72    = bos.entrySet().iterator();
73  1074 iterator.hasNext(); ) {
74  603 Map.Entry entry = (Map.Entry) iterator.next();
75  603 final DefaultKernelQedeqBo prop = (DefaultKernelQedeqBo) entry.getValue();
76  603 prop.delete();
77    }
78  471 bos.clear();
79    } catch (RuntimeException e) {
80  0 Trace.trace(CLASS, this, method, e);
81    } finally {
82  471 Trace.end(CLASS, this, method);
83    }
84    }
85   
86    /**
87    * Validate module dependencies and throw Error if they are not correct.
88    */
 
89  260 toggle synchronized void validateDependencies() {
90  260 final String method = "validateDependencies";
91  260 String url = StringUtils.EMPTY;
92  260 String text = StringUtils.EMPTY;
93  260 boolean error = false;
94  260 Trace.begin(CLASS, this, method);
95    // for debugging: print dependency tree:
96    // for (final Iterator iterator = bos.entrySet().iterator(); iterator.hasNext(); ) {
97    // Map.Entry entry = (Map.Entry) iterator.next();
98    // final DefaultKernelQedeqBo prop = (DefaultKernelQedeqBo) entry.getValue();
99    // prop.getStateManager().printDependencyTree();
100    // }
101  1531 for (final Iterator iterator = bos.entrySet().iterator(); iterator.hasNext(); ) {
102  1271 Map.Entry entry = (Map.Entry) iterator.next();
103  1271 final DefaultKernelQedeqBo prop = (DefaultKernelQedeqBo) entry.getValue();
104  1271 Trace.param(CLASS, this, method, "prop", prop);
105  1271 if (!prop.hasLoadedRequiredModules()) {
106  215 continue;
107    }
108   
109    // prop must be in dependent list for all required modules
110  1056 final KernelModuleReferenceList refs = prop.getKernelRequiredModules();
111  1642 for (int i = 0; i < refs.size(); i++) {
112  586 final DefaultKernelQedeqBo ref = (DefaultKernelQedeqBo) refs.getKernelQedeqBo(i);
113  586 final KernelModuleReferenceList dependents = ref.getDependentModules();
114  586 if (!dependents.contains(prop)) {
115  0 Trace.fatal(CLASS, this, method, ref.getUrl() + " missing dependent module: "
116    + prop.getUrl(), null);
117  0 if (!error) {
118  0 url = ref.getUrl();
119  0 text = "missing dependent module " + prop.getUrl();
120    }
121  0 error = true;
122    }
123    }
124   
125    // for all dependent modules, prop must be in required list
126  1056 final KernelModuleReferenceList dependents = prop.getDependentModules();
127  1754 for (int i = 0; i < dependents.size(); i++) {
128  698 final DefaultKernelQedeqBo dependent
129    = (DefaultKernelQedeqBo) dependents.getKernelQedeqBo(i);
130  698 final KernelModuleReferenceList refs2 = dependent.getKernelRequiredModules();
131  698 if (!refs2.contains(prop)) {
132  0 Trace.fatal(CLASS, this, method, dependent.getUrl()
133    + " missing required module: " + prop.getUrl(), null);
134  0 if (!error) {
135  0 url = prop.getUrl();
136  0 text = "missing required module " + prop.getUrl();
137    }
138  0 error = true;
139    }
140    }
141    }
142  260 Trace.end(CLASS, this, method);
143   
144    // if the dependencies are not ok we throw an error!
145  260 if (error) {
146  0 Error e = new Error("QEDEQ dependencies and status are flawed! "
147    + "This is a major error! We do a kernel shutdown!");
148  0 Trace.fatal(CLASS, this, method, "Shutdown because of major validation error", e);
149  0 QedeqLog.getInstance().logFailureReply(e.getMessage(), url, text);
150  0 KernelContext.getInstance().shutdown();
151  0 throw e;
152    }
153    }
154   
155    /**
156    * Remove a QEDEQ module from memory.
157    *
158    * @param prop Defines the module.
159    */
 
160  0 toggle synchronized void removeModule(final KernelQedeqBo prop) {
161  0 final String method = "removeModule(KernelQedeqBo)";
162  0 Trace.begin(CLASS, this, method);
163  0 try {
164  0 Trace.trace(CLASS, this, method, "removing " + prop.getUrl());
165  0 bos.remove(prop.getModuleAddress());
166    } catch (RuntimeException e) {
167  0 Trace.fatal(CLASS, this, method, "unexpected runtime exception", e);
168  0 throw e;
169    } finally {
170  0 Trace.end(CLASS, this, method);
171    }
172    }
173   
174    /**
175    * Get list of all successfully loaded modules.
176    *
177    * @return list of all successfully loaded modules.
178    */
 
179  471 toggle synchronized ModuleAddress[] getAllLoadedModules() {
180  471 final String method = "getAllModules()";
181  471 Trace.begin(CLASS, this, method);
182  471 try {
183  471 final List list = new ArrayList();
184  1074 for (final Iterator iterator = bos.entrySet().iterator(); iterator.hasNext(); ) {
185  603 Map.Entry entry = (Map.Entry) iterator.next();
186  603 final QedeqBo prop = (QedeqBo) entry.getValue();
187  603 if (prop.getLoadingState().getCode() >= LoadingState.STATE_LOADED.getCode()) {
188  567 list.add(prop.getModuleAddress());
189    }
190    }
191  471 return (ModuleAddress[]) list.toArray(new ModuleAddress[list.size()]);
192    } finally {
193  471 Trace.end(CLASS, this, method);
194    }
195    }
196   
197    }