| 1 11 package org.eclipse.osgi.framework.internal.core; 12 13 import java.io.IOException ; 14 import java.io.InputStream ; 15 import java.net.URL ; 16 import java.net.URLConnection ; 17 import java.security.*; 18 import java.util.*; 19 import org.eclipse.osgi.framework.adaptor.*; 20 import org.eclipse.osgi.framework.debug.Debug; 21 import org.eclipse.osgi.framework.util.KeyedElement; 22 import org.eclipse.osgi.service.resolver.*; 23 import org.eclipse.osgi.util.NLS; 24 import org.osgi.framework.*; 25 26 31 public abstract class AbstractBundle implements Bundle, Comparable , KeyedElement { 32 33 protected Framework framework; 34 35 protected volatile int state; 36 37 protected volatile Thread stateChanging; 38 39 protected BundleData bundledata; 40 41 protected Object statechangeLock = new Object (); 42 43 protected BundleProtectionDomain domain; 44 45 protected ManifestLocalization manifestLocalization = null; 46 47 56 protected static AbstractBundle createBundle(BundleData bundledata, Framework framework) throws BundleException { 57 if ((bundledata.getType() & BundleData.TYPE_FRAGMENT) > 0) 58 return new BundleFragment(bundledata, framework); 59 return new BundleHost(bundledata, framework); 60 } 61 62 71 protected AbstractBundle(BundleData bundledata, Framework framework) { 72 state = INSTALLED; 73 stateChanging = null; 74 this.bundledata = bundledata; 75 this.framework = framework; 76 bundledata.setBundle(this); 77 } 78 79 82 protected abstract void load(); 83 84 93 protected abstract boolean reload(AbstractBundle newBundle); 94 95 101 protected abstract void refresh(); 102 103 110 protected abstract boolean unload(); 111 112 116 protected void close() { 117 if (Debug.DEBUG && Debug.DEBUG_GENERAL) { 118 if ((state & (INSTALLED)) == 0) { 119 Debug.println("Bundle.close called when state != INSTALLED: " + this); Debug.printStackTrace(new Exception ("Stack trace")); } 122 } 123 state = UNINSTALLED; 124 } 125 126 129 protected BundleActivator loadBundleActivator() throws BundleException { 130 131 String activatorClassName = bundledata.getActivator(); 132 if (activatorClassName != null) { 133 try { 134 Class activatorClass = loadClass(activatorClassName, false); 135 136 return (BundleActivator) (activatorClass.newInstance()); 137 } catch (Throwable t) { 138 if (Debug.DEBUG && Debug.DEBUG_GENERAL) { 139 Debug.printStackTrace(t); 140 } 141 throw new BundleException(NLS.bind(Msg.BUNDLE_INVALID_ACTIVATOR_EXCEPTION, activatorClassName, bundledata.getSymbolicName()), t); 142 } 143 } 144 return (null); 145 } 146 147 158 protected abstract Class loadClass(String name, boolean checkPermission) throws ClassNotFoundException ; 159 160 167 public int getState() { 168 return (state); 169 } 170 171 175 protected boolean isActive() { 176 return ((state & (ACTIVE | STARTING)) != 0); 177 } 178 179 183 protected boolean isResolved() { 184 return (state & (INSTALLED | UNINSTALLED)) == 0; 185 } 186 187 251 public void start() throws BundleException { 252 start(0); 253 } 254 255 public void start(int options) throws BundleException { 256 framework.checkAdminPermission(this, AdminPermission.EXECUTE); 257 checkValid(); 258 beginStateChange(); 259 try { 260 startWorker(options); 261 } finally { 262 completeStateChange(); 263 } 264 } 265 266 271 protected abstract void startWorker(int options) throws BundleException; 272 273 286 protected boolean readyToResume() { 287 return false; 288 } 289 290 343 protected void resume() throws BundleException { 344 if (state == UNINSTALLED) { 345 return; 346 } 347 beginStateChange(); 348 try { 349 if (readyToResume()) 350 startWorker(START_TRANSIENT); 351 } finally { 352 completeStateChange(); 353 } 354 } 355 356 416 public void stop() throws BundleException { 417 stop(0); 418 } 419 420 public void stop(int options) throws BundleException { 421 framework.checkAdminPermission(this, AdminPermission.EXECUTE); 422 checkValid(); 423 beginStateChange(); 424 try { 425 stopWorker(options); 426 } finally { 427 completeStateChange(); 428 } 429 } 430 431 436 protected abstract void stopWorker(int options) throws BundleException; 437 438 446 protected void setStatus(final int mask, final boolean state) { 447 try { 448 AccessController.doPrivileged(new PrivilegedExceptionAction() { 449 public Object run() throws BundleException, IOException { 450 int status = bundledata.getStatus(); 451 boolean test = ((status & mask) != 0); 452 if (test != state) { 453 bundledata.setStatus(state ? (status | mask) : (status & ~mask)); 454 bundledata.save(); 455 } 456 return null; 457 } 458 }); 459 } catch (PrivilegedActionException pae) { 460 framework.publishFrameworkEvent(FrameworkEvent.ERROR, this, pae.getException()); 461 } 462 } 463 464 520 protected void suspend(boolean lock) throws BundleException { 521 if (state == UNINSTALLED) { 522 return; 523 } 524 beginStateChange(); 525 try { 526 stopWorker(STOP_TRANSIENT); 527 } finally { 528 if (!lock) { 529 completeStateChange(); 530 } 531 } 532 } 533 534 595 public void update() throws BundleException { 596 if (Debug.DEBUG && Debug.DEBUG_GENERAL) { 597 Debug.println("update location " + bundledata.getLocation()); } 599 framework.checkAdminPermission(this, AdminPermission.LIFECYCLE); 600 if ((bundledata.getType() & (BundleData.TYPE_BOOTCLASSPATH_EXTENSION | BundleData.TYPE_FRAMEWORK_EXTENSION)) != 0) 601 framework.checkAdminPermission(this, AdminPermission.EXTENSIONLIFECYCLE); 603 checkValid(); 604 beginStateChange(); 605 try { 606 final AccessControlContext callerContext = AccessController.getContext(); 607 updateWorker(new PrivilegedExceptionAction() { 609 public Object run() throws BundleException { 610 611 String updateLocation = bundledata.getLocation(); 612 if (bundledata.getManifest().get(Constants.BUNDLE_UPDATELOCATION) != null) { 613 updateLocation = (String ) bundledata.getManifest().get(Constants.BUNDLE_UPDATELOCATION); 614 if (Debug.DEBUG && Debug.DEBUG_GENERAL) { 615 Debug.println(" from location: " + updateLocation); } 617 } 618 619 URLConnection source = framework.adaptor.mapLocationToURLConnection(updateLocation); 620 621 updateWorkerPrivileged(source, callerContext); 622 return null; 623 } 624 }); 625 } finally { 626 completeStateChange(); 627 } 628 } 629 630 642 public void update(final InputStream in) throws BundleException { 643 if (Debug.DEBUG && Debug.DEBUG_GENERAL) { 644 Debug.println("update location " + bundledata.getLocation()); Debug.println(" from: " + in); } 647 framework.checkAdminPermission(this, AdminPermission.LIFECYCLE); 648 if ((bundledata.getType() & (BundleData.TYPE_BOOTCLASSPATH_EXTENSION | BundleData.TYPE_FRAMEWORK_EXTENSION)) != 0) 649 framework.checkAdminPermission(this, AdminPermission.EXTENSIONLIFECYCLE); 651 checkValid(); 652 beginStateChange(); 653 try { 654 final AccessControlContext callerContext = AccessController.getContext(); 655 updateWorker(new PrivilegedExceptionAction() { 657 public Object run() throws BundleException { 658 659 URLConnection source = new BundleSource(in); 660 661 updateWorkerPrivileged(source, callerContext); 662 return null; 663 } 664 }); 665 } finally { 666 completeStateChange(); 667 } 668 } 669 670 673 protected void updateWorker(PrivilegedExceptionAction action) throws BundleException { 674 boolean bundleActive = false; 675 if (!isFragment()) 676 bundleActive = (state & (ACTIVE | STARTING)) != 0; 677 if (bundleActive) { 678 try { 679 stopWorker(STOP_TRANSIENT); 680 } catch (BundleException e) { 681 framework.publishFrameworkEvent(FrameworkEvent.ERROR, this, e); 682 if ((state & (ACTIVE | STARTING)) != 0) { 683 throw e; 684 } 685 } 686 } 687 try { 688 AccessController.doPrivileged(action); 689 framework.publishBundleEvent(BundleEvent.UPDATED, this); 690 } catch (PrivilegedActionException pae) { 691 if (pae.getException() instanceof RuntimeException ) 692 throw (RuntimeException ) pae.getException(); 693 throw (BundleException) pae.getException(); 694 } finally { 695 if (bundleActive) { 696 try { 697 startWorker(START_TRANSIENT); 698 } catch (BundleException e) { 699 framework.publishFrameworkEvent(FrameworkEvent.ERROR, this, e); 700 } 701 } 702 } 703 } 704 705 708 protected void updateWorkerPrivileged(URLConnection source, AccessControlContext callerContext) throws BundleException { 709 AbstractBundle oldBundle = AbstractBundle.createBundle(bundledata, framework); 710 boolean reloaded = false; 711 BundleOperation storage = framework.adaptor.updateBundle(this.bundledata, source); 712 BundleRepository bundles = framework.getBundles(); 713 try { 714 BundleData newBundleData = storage.begin(); 715 final AbstractBundle newBundle = framework.createAndVerifyBundle(newBundleData); 717 String [] nativepaths = framework.selectNativeCode(newBundle); 718 if (nativepaths != null) { 719 newBundleData.installNativeCode(nativepaths); 720 } 721 boolean exporting; 722 int st = getState(); 723 synchronized (bundles) { 724 exporting = reload(newBundle); 725 manifestLocalization = null; 726 } 727 reloaded = true; 729 if (System.getSecurityManager() != null) { 730 final boolean extension = (bundledata.getType() & (BundleData.TYPE_BOOTCLASSPATH_EXTENSION | BundleData.TYPE_FRAMEWORK_EXTENSION)) != 0; 731 if (extension && !hasPermission(new AllPermission())) 733 throw new BundleException(Msg.BUNDLE_EXTENSION_PERMISSION, new SecurityException (Msg.BUNDLE_EXTENSION_PERMISSION)); 734 try { 735 AccessController.doPrivileged(new PrivilegedExceptionAction() { 736 public Object run() throws Exception { 737 framework.checkAdminPermission(newBundle, AdminPermission.LIFECYCLE); 738 if (extension) framework.checkAdminPermission(newBundle, AdminPermission.EXTENSIONLIFECYCLE); 740 return null; 741 } 742 }, callerContext); 743 } catch (PrivilegedActionException e) { 744 throw e.getException(); 745 } 746 } 747 if (st == RESOLVED) 749 framework.publishBundleEvent(BundleEvent.UNRESOLVED, this); 750 storage.commit(exporting); 751 } catch (Throwable t) { 752 try { 753 storage.undo(); 754 if (reloaded) { 758 synchronized (bundles) { 759 reload(oldBundle); 760 } 761 } 762 } catch (BundleException ee) { 763 764 framework.publishFrameworkEvent(FrameworkEvent.ERROR, this, ee); 765 } 766 if (t instanceof SecurityException ) 767 throw (SecurityException ) t; 768 if (t instanceof BundleException) 769 throw (BundleException) t; 770 throw new BundleException(t.getMessage(), t); 771 } 772 } 773 774 822 public void uninstall() throws BundleException { 823 if (Debug.DEBUG && Debug.DEBUG_GENERAL) { 824 Debug.println("uninstall location: " + bundledata.getLocation()); } 826 framework.checkAdminPermission(this, AdminPermission.LIFECYCLE); 827 if ((bundledata.getType() & (BundleData.TYPE_BOOTCLASSPATH_EXTENSION | BundleData.TYPE_FRAMEWORK_EXTENSION)) != 0) 828 framework.checkAdminPermission(this, AdminPermission.EXTENSIONLIFECYCLE); 830 checkValid(); 831 beginStateChange(); 832 try { 833 uninstallWorker(new PrivilegedExceptionAction() { 834 public Object run() throws BundleException { 835 uninstallWorkerPrivileged(); 836 return null; 837 } 838 }); 839 } finally { 840 completeStateChange(); 841 } 842 } 843 844 847 protected void uninstallWorker(PrivilegedExceptionAction action) throws BundleException { 848 boolean bundleActive = false; 849 if (!isFragment()) 850 bundleActive = (state & (ACTIVE | STARTING)) != 0; 851 if (bundleActive) { 852 try { 853 stopWorker(STOP_TRANSIENT); 854 } catch (BundleException e) { 855 framework.publishFrameworkEvent(FrameworkEvent.ERROR, this, e); 856 } 857 } 858 try { 859 AccessController.doPrivileged(action); 860 } catch (PrivilegedActionException pae) { 861 if (bundleActive) { 862 try { 863 startWorker(START_TRANSIENT); 864 } catch (BundleException e) { 865 869 framework.publishFrameworkEvent(FrameworkEvent.ERROR, this, e); 870 } 871 } 872 throw (BundleException) pae.getException(); 873 } 874 framework.publishBundleEvent(BundleEvent.UNINSTALLED, this); 875 } 876 877 880 protected void uninstallWorkerPrivileged() throws BundleException { 881 if (Debug.DEBUG) { 882 BundleWatcher bundleStats = framework.adaptor.getBundleWatcher(); 883 &n
|