Permissions

沒有執行安全管理器的 Tomcat 訪問控制異常(綁定到 RMI)(Ubuntu)

  • June 14, 2013

我遇到了來自 Tomcat servlet 的一些奇怪的訪問控制異常(當它嘗試綁定到 RMI 伺服器時)。我在沒有安全管理器的情況下執行,整個應用程序以前在基本相同的設置上執行良好。

這是對我所在的 webapp 的類文件夾的 java.io.FilePermission 訪問被拒絕。當我將我的 RMI 存根重新綁定到 RMI 系統資料庫時發生錯誤(這是我訪問了相同的其他一些類之後webapp,在我導出存根並找到系統資料庫之後;做了一些日誌消息來證明這一點)。任何幫助都會很棒,因為我現在已經死在這個水里了……

更新:好的,取得了一些進展(此更新覆蓋了以前的假設)。這與 RMI 系統資料庫的程式碼庫訪問有關,並且可能與 OpenJDK 的一些怪癖有關。

當我將伺服器綁定到系統資料庫時,它會嘗試通過它認為是程式碼庫的方式訪問相關類。看來,使用系統資料庫用於獲取程式碼庫位置的任何隱蔽 RMI 魔法,它以某種方式無法獲取 JVM 屬性中的那個,而是試圖查看 webapp 的類路徑(??)。

推理(!):這曾經適用於程式碼庫的文件 URL(並且沒有 Java 安全策略)。我在 Tomcat 之外測試了 RMI 伺服器設置(就像 POJO 一樣),它使用HTTP URL而不是文件 URL。後者給出了與 Tomcat 中相同的訪問權限錯誤,但顯示它試圖訪問這個特定的文件位置(與 Tomcat 中它試圖訪問完全不同的位置不同)。我懷疑文件 URL 的失敗可能是由於 OpenJDK 和 Sun JDK 之間的差異。(我以前用過 Sun 的;我只記得。)

但是,當我嘗試使用 Tomcat 設置的工作 HTTP URL(確保服務它的 Web 伺服器位於與 Tomcat 不同的埠上)時,它仍然像嘗試訪問 webapp 的類路徑區域一樣失敗。我已經在 servlet 程式碼中確認 java.rmi.server.codebase 屬性設置正確(所以它可以通過 servlet 程式碼)。也許是 OpenJDK rmiregistry 中的一個錯誤(似乎不太可能)?

這是否有助於任何人有更多的想法?這是否更好地放置在 StackOverflow 上(有人可能會爭辯說它在我認為的任何一個位置)?

使用 Tomcat 6.0.24 本地環境,由 Ubuntu 10.04 x64 和 OpenJDK 1.6.0_20 上的 tomcat6-instance-create cmd 創建。(所有 Ubuntu 10.04 的預設設置。)

異常跟踪如下:

simHAWSER.core.exceptions.HAWSER_RMI_ConfigurationException: Error setting up observer gateway server HAWSER_ObserverGateway
   at simHAWSER.core.internal.yawlInterface.HAWSER_ObserverGateway.announceEngineInitialised(HAWSER_ObserverGateway.java:1404)
   at org.yawlfoundation.yawl.engine.ObserverGatewayController$8.run(ObserverGatewayController.java:278)
   at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1110)
   at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:603)
   at java.lang.Thread.run(Thread.java:636)
Caused by: java.rmi.ServerException: RemoteException occurred in server thread; nested exception is: 
   java.rmi.UnmarshalException: error unmarshalling arguments; nested exception is: 
   java.lang.ClassNotFoundException: access to class loader denied
   at sun.rmi.server.UnicastServerRef.oldDispatch(UnicastServerRef.java:419)
   at sun.rmi.server.UnicastServerRef.dispatch(UnicastServerRef.java:267)
   at sun.rmi.transport.Transport$1.run(Transport.java:177)
   at java.security.AccessController.doPrivileged(Native Method)
   at sun.rmi.transport.Transport.serviceCall(Transport.java:173)
   at sun.rmi.transport.tcp.TCPTransport.handleMessages(TCPTransport.java:553)
   at sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.run0(TCPTransport.java:808)
   at sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.run(TCPTransport.java:667)
   at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1110)
   at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:603)
   at java.lang.Thread.run(Thread.java:636)
   at sun.rmi.transport.StreamRemoteCall.exceptionReceivedFromServer(StreamRemoteCall.java:273)
   at sun.rmi.transport.StreamRemoteCall.executeCall(StreamRemoteCall.java:251)
   at sun.rmi.server.UnicastRef.invoke(UnicastRef.java:377)
   at sun.rmi.registry.RegistryImpl_Stub.rebind(Unknown Source)
   at simHAWSER.core.internal.yawlInterface.HAWSER_ObserverGateway.announceEngineInitialised(HAWSER_ObserverGateway.java:1400)
   ... 4 more
Caused by: java.rmi.UnmarshalException: error unmarshalling arguments; nested exception is: 
   java.lang.ClassNotFoundException: access to class loader denied
   at sun.rmi.registry.RegistryImpl_Skel.dispatch(Unknown Source)
   at sun.rmi.server.UnicastServerRef.oldDispatch(UnicastServerRef.java:409)
   at sun.rmi.server.UnicastServerRef.dispatch(UnicastServerRef.java:267)
   at sun.rmi.transport.Transport$1.run(Transport.java:177)
   at java.security.AccessController.doPrivileged(Native Method)
   at sun.rmi.transport.Transport.serviceCall(Transport.java:173)
   at sun.rmi.transport.tcp.TCPTransport.handleMessages(TCPTransport.java:553)
   at sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.run0(TCPTransport.java:808)
   at sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.run(TCPTransport.java:667)
   ... 3 more
Caused by: java.lang.ClassNotFoundException: access to class loader denied
   at sun.rmi.server.LoaderHandler.loadProxyClass(LoaderHandler.java:603)
   at java.rmi.server.RMIClassLoader$2.loadProxyClass(RMIClassLoader.java:646)
   at java.rmi.server.RMIClassLoader.loadProxyClass(RMIClassLoader.java:311)
   at sun.rmi.server.MarshalInputStream.resolveProxyClass(MarshalInputStream.java:255)
   at java.io.ObjectInputStream.readProxyDesc(ObjectInputStream.java:1548)
   at java.io.ObjectInputStream.readClassDesc(ObjectInputStream.java:1510)
   at java.io.ObjectInputStream.readOrdinaryObject(ObjectInputStream.java:1749)
   at java.io.ObjectInputStream.readObject0(ObjectInputStream.java:1346)
   at java.io.ObjectInputStream.readObject(ObjectInputStream.java:368)
   ... 12 more
Caused by: java.security.AccessControlException: access denied (java.io.FilePermission /home/rigsby/Build/yawl/r1803/tomcat6/webapps/yawl/WEB-INF/classes/- read)
   at java.security.AccessControlContext.checkPermission(AccessControlContext.java:393)
   at java.security.AccessController.checkPermission(AccessController.java:553)
   at java.lang.SecurityManager.checkPermission(SecurityManager.java:549)
   at sun.rmi.server.LoaderHandler$Loader.checkPermissions(LoaderHandler.java:1173)
   at sun.rmi.server.LoaderHandler$Loader.access$000(LoaderHandler.java:1127)
   at sun.rmi.server.LoaderHandler.loadProxyClass(LoaderHandler.java:569)
   ... 20 more

原始 simHAWSER 類是我的應用程序(作為 yawl webapp 的一部分執行)。如果有任何影響,我的程式碼在 webapp lib 目錄中作為單獨的 JAR 執行,並由 yawl servlet(部署到正常的類目錄)呼叫。

在半絕望中,我嘗試使用安全管理器啟動 Tomcat(授予此 web 應用程序的所有權限),但這在讀取我的 catalina.policy 文件時導致了一些奇怪的“空 KeyStore 名稱”異常(我只是從這裡複製了預設的.) 無論如何,我知道它在沒有安全性的情況下工作(並且應該工作),所以不想在這個方向上大打出手:-)

如果有人想要更多細節,請告訴我。

PS 想要添加一個 RMI 標籤(或 rmiregistry 以匹配StackOverflow),但沒有它的代表 :-( 如果有人想添加它,那就太好了。

好的,解決了。問題在於使用 OpenJDK 而不是 Sun Java。OpenJDKrmiregistry實現不喜歡文件 URL(訪問異常),並且當嘗試訪問 Tomcat webapp 的程式碼庫屬性時,它以某種方式無法正確看到它(假設與 Tomcat 中使用的 per-webapp 類載入器有關搞砸了)。

切換到 Sunrmiregistry實現(即使保留對 Tomcat 的 OpenJDK 的使用)意味著它可以正常工作。如果我在這方面找不到任何 OpenJDK 錯誤,我會提出一個並在此處連結到它以確保完整性。

我懷疑 OpenJDK 的文件 URL 問題是由於不同的預設(無顯式 java 策略)安全設置,我可以使用顯式策略文件來使其工作……

希望這對其他人有所幫助,因為它確實令人頭疼。

引用自:https://serverfault.com/questions/347293