1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16 package org.qedeq.kernel.bo;
17
18 import java.io.File;
19 import java.io.FileOutputStream;
20 import java.io.IOException;
21 import java.net.URL;
22 import java.nio.channels.FileLock;
23
24 import org.qedeq.base.io.IoUtility;
25 import org.qedeq.base.trace.Trace;
26 import org.qedeq.base.utility.StringUtility;
27 import org.qedeq.kernel.bo.common.BasicKernel;
28 import org.qedeq.kernel.bo.common.KernelProperties;
29 import org.qedeq.kernel.bo.common.KernelServices;
30 import org.qedeq.kernel.bo.common.KernelState;
31 import org.qedeq.kernel.bo.common.QedeqBo;
32 import org.qedeq.kernel.bo.common.Kernel;
33 import org.qedeq.kernel.bo.common.ServiceJob;
34 import org.qedeq.kernel.bo.log.QedeqLog;
35 import org.qedeq.kernel.se.common.ModuleAddress;
36 import org.qedeq.kernel.se.common.ModuleService;
37 import org.qedeq.kernel.se.config.QedeqConfig;
38 import org.qedeq.kernel.se.visitor.InterruptException;
39
40
41
42
43
44
45
46 public final class KernelContext implements KernelProperties, KernelServices {
47
48
49 private static final String KERNEL_NOT_STARTED = "Kernel not started";
50
51
52 private static final String KERNEL_NOT_INITIALIZED = "Kernel not initialized";
53
54
55 private static final Class CLASS = KernelContext.class;
56
57
58 private static final KernelContext INSTANCE = new KernelContext();
59
60
61 private File lockFile;
62
63
64 private FileOutputStream lockStream;
65
66
67 private final KernelState initialState = new KernelState() {
68
69 public void init(final QedeqConfig config, final Kernel moduleServices, final KernelProperties basic)
70 throws IOException {
71 if (config == null) {
72 throw new NullPointerException("QedeqConfig is null");
73 }
74 if (moduleServices == null) {
75 throw new NullPointerException("ServiceModule is null");
76 }
77 if (basic == null) {
78 throw new NullPointerException("KernelProperties is null");
79 }
80 KernelContext.this.config = config;
81 KernelContext.this.basic = basic;
82 Trace.setTraceOn(config.isTraceOn());
83 checkJavaVersion();
84 createAllNecessaryDirectories();
85 checkIfApplicationIsAlreadyRunningAndLockFile();
86 KernelContext.this.services = moduleServices;
87 QedeqLog.getInstance().logMessage("--------------------------------------------------"
88 + "---------------------------------------");
89 QedeqLog.getInstance().logMessage("This is "
90 + KernelContext.getInstance().getDescriptiveKernelVersion());
91 QedeqLog.getInstance().logMessage(" see \"http://www.qedeq.org\" for more "
92 + "information");
93 QedeqLog.getInstance().logMessage(" supports rules till version "
94 + KernelContext.getInstance().getMaximalRuleVersion());
95 QedeqLog.getInstance().logMessage(" Java version: "
96 + StringUtility.alignRight(System.getProperty("java.version", "unknown"), 10));
97 QedeqLog.getInstance().logMessage(" used memory: "
98 + StringUtility.alignRight(Runtime.getRuntime().totalMemory()
99 - Runtime.getRuntime().freeMemory(), 10));
100 QedeqLog.getInstance().logMessage(" free memory: "
101 + StringUtility.alignRight(Runtime.getRuntime().freeMemory(), 10));
102 QedeqLog.getInstance().logMessage(" total memory: "
103 + StringUtility.alignRight(Runtime.getRuntime().totalMemory(), 10));
104 QedeqLog.getInstance().logMessage(" max. memory: "
105 + StringUtility.alignRight(Runtime.getRuntime().maxMemory(), 10));
106 QedeqLog.getInstance().logMessage(" processors/cores: "
107 + StringUtility.alignRight(Runtime.getRuntime().availableProcessors(), 6));
108 currentState = initializedState;
109 }
110
111 public void startup() {
112 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
113 }
114
115 public void shutdown() {
116 currentState = initialState;
117
118 IoUtility.close(lockStream);
119 lockStream = null;
120 config = null;
121 services = null;
122 }
123
124 public boolean removeAllModules() {
125 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
126 }
127
128 public void removeModule(final ModuleAddress address) {
129 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
130 }
131
132 public boolean clearLocalBuffer() {
133 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
134 }
135
136 public QedeqBo loadModule(final ModuleAddress address) {
137 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
138 }
139
140 public boolean loadAllModulesFromQedeq() {
141 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
142 }
143
144 public boolean loadRequiredModules(final ModuleAddress address) {
145 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
146 }
147
148 public ModuleAddress[] getAllLoadedModules() {
149 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
150 }
151
152 public QedeqBo getQedeqBo(final ModuleAddress address) {
153 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
154 }
155
156 public ModuleAddress getModuleAddress(final URL url) {
157 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
158 }
159
160 public ModuleAddress getModuleAddress(final String url) {
161 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
162 }
163
164 public ModuleAddress getModuleAddress(final File file) {
165 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
166 }
167
168 public String getSource(final ModuleAddress address) {
169 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
170 }
171
172 public boolean checkWellFormedness(final ModuleAddress address) {
173 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
174 }
175
176 public boolean checkFormallyProved(final ModuleAddress address) {
177 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
178 }
179
180 public ModuleService[] getPlugins() {
181 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
182 }
183
184 public Object executePlugin(final String pluginName, final ModuleAddress address,
185 final Object data) {
186 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
187 }
188
189 public void clearAllPluginResults(final ModuleAddress address) {
190 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
191 }
192
193 public ServiceJob[] getServiceProcesses() {
194 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
195 }
196
197 public ServiceJob[] getRunningServiceProcesses() {
198 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
199 }
200
201 public void terminateAllServiceProcesses() {
202 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
203 }
204
205 };
206
207
208 private final KernelState initializedState = new KernelState() {
209
210 public void init(final QedeqConfig config, final Kernel moduleServices,
211 final KernelProperties basic) throws IOException {
212 throw new IllegalStateException("Kernel is already initialized");
213 }
214
215 public void startup() {
216 services.startupServices();
217 currentState = readyState;
218 QedeqLog.getInstance().logMessage("QEDEQ kernel opened.");
219 }
220
221 public void shutdown() {
222 services.shutdownServices();
223 KernelContext.this.services = null;
224 initialState.shutdown();
225 QedeqLog.getInstance().logMessage("QEDEQ Kernel closed.");
226 }
227
228 public boolean removeAllModules() {
229 throw new IllegalStateException(KERNEL_NOT_STARTED);
230 }
231
232 public void removeModule(final ModuleAddress address) {
233 throw new IllegalStateException(KERNEL_NOT_STARTED);
234 }
235
236 public boolean clearLocalBuffer() {
237 throw new IllegalStateException(KERNEL_NOT_STARTED);
238 }
239
240 public QedeqBo loadModule(final ModuleAddress address) {
241 throw new IllegalStateException(KERNEL_NOT_STARTED);
242 }
243
244 public boolean loadAllModulesFromQedeq() {
245 throw new IllegalStateException(KERNEL_NOT_STARTED);
246 }
247
248 public boolean loadRequiredModules(final ModuleAddress address) {
249 throw new IllegalStateException(KERNEL_NOT_STARTED);
250 }
251
252 public ModuleAddress[] getAllLoadedModules() {
253 throw new IllegalStateException(KERNEL_NOT_STARTED);
254 }
255
256 public QedeqBo getQedeqBo(final ModuleAddress address) {
257 throw new IllegalStateException(KERNEL_NOT_STARTED);
258 }
259
260 public ModuleAddress getModuleAddress(final URL url) {
261 throw new IllegalStateException(KERNEL_NOT_STARTED);
262 }
263
264 public ModuleAddress getModuleAddress(final String url) {
265 throw new IllegalStateException(KERNEL_NOT_STARTED);
266 }
267
268 public ModuleAddress getModuleAddress(final File file) {
269 throw new IllegalStateException(KERNEL_NOT_STARTED);
270 }
271
272 public String getSource(final ModuleAddress address) {
273 throw new IllegalStateException(KERNEL_NOT_STARTED);
274 }
275
276 public boolean checkWellFormedness(final ModuleAddress address) {
277 throw new IllegalStateException(KERNEL_NOT_STARTED);
278 }
279
280 public boolean checkFormallyProved(final ModuleAddress address) {
281 throw new IllegalStateException(KERNEL_NOT_INITIALIZED);
282 }
283
284 public ModuleService[] getPlugins() {
285 return services.getPlugins();
286 }
287
288 public Object executePlugin(final String pluginName, final ModuleAddress address,
289 final Object data) {
290 throw new IllegalStateException(KERNEL_NOT_STARTED);
291 }
292
293 public void clearAllPluginResults(final ModuleAddress address) {
294 throw new IllegalStateException(KERNEL_NOT_STARTED);
295 }
296
297 public ServiceJob[] getServiceProcesses() {
298 throw new IllegalStateException(KERNEL_NOT_STARTED);
299 }
300
301 public ServiceJob[] getRunningServiceProcesses() {
302 throw new IllegalStateException(KERNEL_NOT_STARTED);
303 }
304
305 public void terminateAllServiceProcesses() {
306 throw new IllegalStateException(KERNEL_NOT_STARTED);
307 }
308
309 };
310
311
312 private final KernelState readyState = new KernelState() {
313
314 public void init(final QedeqConfig config, final Kernel moduleServices,
315 final KernelProperties basic) throws IOException {
316
317 }
318
319 public void startup() {
320
321 }
322
323 public void shutdown() {
324 try {
325 final ModuleAddress[] addresses = services.getAllLoadedModules();
326 if (addresses != null) {
327 final String[] buffer = new String[addresses.length];
328 for (int i = 0; i < addresses.length; i++) {
329 buffer[i] = addresses[i].toString();
330 }
331 getConfig().setPreviouslyLoadedModules(buffer);
332 getConfig().store();
333 QedeqLog.getInstance().logMessage("Current config file successfully saved.");
334 }
335 } catch (IOException e) {
336 Trace.trace(CLASS, this, "shutdown()", e);
337 QedeqLog.getInstance().logMessage("Saving current config file failed.");
338 }
339 initializedState.shutdown();
340 }
341
342 public boolean removeAllModules() {
343 return services.removeAllModules();
344 }
345
346 public void removeModule(final ModuleAddress address) {
347 services.removeModule(address);
348 }
349
350 public boolean clearLocalBuffer() {
351 return services.clearLocalBuffer();
352 }
353
354 public QedeqBo loadModule(final ModuleAddress address) {
355 return services.loadModule(address);
356 }
357
358 public boolean loadAllModulesFromQedeq() {
359 return services.loadAllModulesFromQedeq();
360 }
361
362 public boolean loadRequiredModules(final ModuleAddress address) {
363 return services.loadRequiredModules(address);
364 }
365
366 public ModuleAddress[] getAllLoadedModules() {
367 return services.getAllLoadedModules();
368 }
369
370 public QedeqBo getQedeqBo(final ModuleAddress address) {
371 return services.getQedeqBo(address);
372 }
373
374 public ModuleAddress getModuleAddress(final URL url) throws IOException {
375 return services.getModuleAddress(url);
376 }
377
378 public ModuleAddress getModuleAddress(final String url) throws IOException {
379 return services.getModuleAddress(url);
380 }
381
382 public ModuleAddress getModuleAddress(final File file) throws IOException {
383 return services.getModuleAddress(file);
384 }
385
386 public String getSource(final ModuleAddress address) throws IOException {
387 return services.getSource(address);
388 }
389
390 public boolean checkWellFormedness(final ModuleAddress address) {
391 return services.checkWellFormedness(address);
392 }
393
394 public boolean checkFormallyProved(final ModuleAddress address) {
395 return services.checkFormallyProved(address);
396 }
397
398 public ModuleService[] getPlugins() {
399 return services.getPlugins();
400 }
401
402 public Object executePlugin(final String pluginName, final ModuleAddress address,
403 final Object data) throws InterruptException {
404 return services.executePlugin(pluginName, address, data);
405 }
406
407 public void clearAllPluginResults(final ModuleAddress address) {
408 services.clearAllPluginResults(address);
409 }
410
411 public ServiceJob[] getServiceProcesses() {
412 return services.getServiceProcesses();
413 }
414
415 public ServiceJob[] getRunningServiceProcesses() {
416 return services.getRunningServiceProcesses();
417 }
418
419 public void terminateAllServiceProcesses() {
420 services.terminateAllServiceProcesses();
421 }
422
423 };
424
425
426 private QedeqConfig config;
427
428
429 private KernelState currentState = initialState;
430
431
432 private KernelProperties basic;
433
434
435 private Kernel services;
436
437
438
439
440 private KernelContext() {
441 basic = new BasicKernel();
442 }
443
444
445
446
447
448
449 public static final KernelContext getInstance() {
450 return INSTANCE;
451 }
452
453 public String getBuildId() {
454 return basic.getBuildId();
455 }
456
457 public final String getKernelVersion() {
458 return basic.getKernelVersion();
459 }
460
461 public final String getKernelCodeName() {
462 return basic.getKernelCodeName();
463 }
464
465 public final String getKernelVersionDirectory() {
466 return basic.getKernelVersionDirectory();
467 }
468
469 public final String getDescriptiveKernelVersion() {
470 return basic.getDescriptiveKernelVersion();
471 }
472
473 public final String getDedication() {
474 return basic.getDedication();
475 }
476
477 public final String getMaximalRuleVersion() {
478 return basic.getMaximalRuleVersion();
479 }
480
481 public final boolean isRuleVersionSupported(final String ruleVersion) {
482 return basic.isRuleVersionSupported(ruleVersion);
483 }
484
485 public boolean isSetConnectionTimeOutSupported() {
486 return basic.isSetConnectionTimeOutSupported();
487 }
488
489 public boolean isSetReadTimeoutSupported() {
490 return basic.isSetReadTimeoutSupported();
491 }
492
493 public QedeqConfig getConfig() {
494 return config;
495 }
496
497
498
499
500
501
502
503
504
505 public void init(final QedeqConfig config, final Kernel moduleServices) throws IOException {
506 currentState.init(config, moduleServices, basic);
507 }
508
509
510
511
512 public void startup() {
513 currentState.startup();
514 }
515
516
517
518
519 public void shutdown() {
520 currentState.shutdown();
521 }
522
523 public boolean removeAllModules() {
524 return currentState.removeAllModules();
525 }
526
527 public void removeModule(final ModuleAddress address) {
528 currentState.removeModule(address);
529 }
530
531 public boolean clearLocalBuffer() {
532 return currentState.clearLocalBuffer();
533 }
534
535 public QedeqBo loadModule(final ModuleAddress address) {
536 return currentState.loadModule(address);
537 }
538
539 public boolean loadAllModulesFromQedeq() {
540 return currentState.loadAllModulesFromQedeq();
541 }
542
543 public boolean loadRequiredModules(final ModuleAddress address) {
544 return currentState.loadRequiredModules(address);
545 }
546
547 public ModuleAddress[] getAllLoadedModules() {
548 return currentState.getAllLoadedModules();
549 }
550
551 public QedeqBo getQedeqBo(final ModuleAddress address) {
552 return currentState.getQedeqBo(address);
553 }
554
555 public ModuleAddress getModuleAddress(final URL url) throws IOException {
556 return currentState.getModuleAddress(url);
557 }
558
559 public ModuleAddress getModuleAddress(final String url) throws IOException {
560 return currentState.getModuleAddress(url);
561 }
562
563 public ModuleAddress getModuleAddress(final File file) throws IOException {
564 return currentState.getModuleAddress(file);
565 }
566
567 public String getSource(final ModuleAddress address) throws IOException {
568 return currentState.getSource(address);
569 }
570
571 public boolean checkWellFormedness(final ModuleAddress address) {
572 return currentState.checkWellFormedness(address);
573 }
574
575 public boolean checkFormallyProved(final ModuleAddress address) {
576 return currentState.checkFormallyProved(address);
577 }
578
579 public ModuleService[] getPlugins() {
580 return currentState.getPlugins();
581 }
582
583 public Object executePlugin(final String pluginName, final ModuleAddress address,
584 final Object data) throws InterruptException {
585 return currentState.executePlugin(pluginName, address, data);
586 }
587
588 public void clearAllPluginResults(final ModuleAddress address) {
589 currentState.clearAllPluginResults(address);
590 }
591
592 public ServiceJob[] getServiceProcesses() {
593 return currentState.getServiceProcesses();
594 }
595
596 public ServiceJob[] getRunningServiceProcesses() {
597 return currentState.getRunningServiceProcesses();
598 }
599
600 public void terminateAllServiceProcesses() {
601 currentState.terminateAllServiceProcesses();
602 }
603
604
605
606
607
608
609 private void checkJavaVersion() throws IOException {
610 final String method = "checkJavaVersion";
611 Trace.info(CLASS, this, method, "running on java version "
612 + System.getProperty("java.version"));
613 final int[] versions = IoUtility.getJavaVersion();
614 if (versions == null) {
615 Trace.fatal(CLASS, this, method, "running java version unknown", null);
616
617 return;
618 }
619 final StringBuffer version = new StringBuffer();
620 for (int i = 0; i < versions.length; i++) {
621 if (i > 0) {
622 version.append(".");
623 }
624 version.append(versions[i]);
625 }
626 Trace.paramInfo(CLASS, this, method, "version", version);
627
628 if (versions.length < 1 || versions[0] < 1) {
629 throw new IOException("This application requires at least Java 1.4.2 but we got "
630 + version);
631 }
632 if (versions[0] == 1) {
633
634 if (versions.length < 2 || versions[1] < 4) {
635 throw new IOException("This application requires at least Java 1.4.2 but we got "
636 + version);
637 }
638 if (versions[1] == 4) {
639
640 if (versions.length < 3 || versions[2] < 2) {
641 throw new IOException(
642 "This application requires at least Java 1.4.2 but we got "
643 + version);
644 }
645 }
646 }
647 }
648
649
650
651
652
653
654 void createAllNecessaryDirectories() throws IOException {
655
656 final File logFile = getConfig().getLogFile();
657 final File logDir = logFile.getParentFile();
658 if (!logDir.exists() && !logDir.mkdirs()) {
659 throw new IOException("can't create directory: " + logDir.getAbsolutePath());
660 }
661
662 final File bufferDir = getConfig().getBufferDirectory();
663 if (!bufferDir.exists() && !bufferDir.mkdirs()) {
664 throw new IOException("can't create directory: " + bufferDir.getAbsolutePath());
665 }
666
667 final File generationDir = getConfig().getGenerationDirectory();
668 if (!generationDir.exists() && !generationDir.mkdirs()) {
669 throw new IOException("can't create directory: " + generationDir.getAbsolutePath());
670 }
671 }
672
673
674
675
676
677
678
679
680 private void checkIfApplicationIsAlreadyRunningAndLockFile()
681 throws IOException {
682 lockFile = new File(getConfig().getBufferDirectory(), "qedeq_lock.lck");
683 FileLock fl = null;
684 try {
685 lockStream = new FileOutputStream(lockFile);
686 lockStream.write("LOCKED".getBytes("UTF8"));
687 lockStream.flush();
688 fl = lockStream.getChannel().tryLock();
689 } catch (IOException e) {
690 throw new IOException("It seems the application is already running.\n"
691 + "At least accessing the file \"" + lockFile.getAbsolutePath() + "\" failed.");
692 }
693 if (fl == null) {
694 throw new IOException("It seems the application is already running.\n"
695 + "At least locking the file \"" + lockFile.getAbsolutePath() + "\" failed.");
696 }
697 }
698
699 }