zoukankan      html  css  js  c++  java
  • java安全-安全管理器

    基本概念

    安全管理器是一个负责控制具体操作是否允许执行的类,它主要负责检查的操作包括如下内容:

    • 创建一个新的类加载器;
    • 退出虚拟机
    • 使用反射访问另一个类的成员
    • 访问本地文件
    • 打开socket连接
    • 启动打印作业
    • 访问系统剪贴板
    • 打开一个顶层窗口

    java.lang.SecurityManager类包含了很多checkXXXX方法,SecurityManager 中其他所有 check 方法的默认实现都是调用 SecurityManager checkPermission 方法来确定调用线程是否具有执行所请求操作的权限。
    权限分为以下类别:文件、套接字、网络、安全性、运行时、属性、AWT、反射和可序列化。管理各种权限类别的类是 java.io.FilePermission、java.net.SocketPermission、java.net.NetPermission、java.security.SecurityPermission、java.lang.RuntimePermission、java.util.PropertyPermission、java.awt.AWTPermission、java.lang.reflect.ReflectPermission 和 java.io.SerializablePermission。

    除前两个(FilePermission 和 SocketPermission)类以外的所有类都是 java.security.BasicPermission 的子类,而 java.security.BasicPermission 类又是顶级权限类 java.security.Permission 的抽象子类。

    安全策略文件:
    类装载器用Policy对象帮助它们决定,把一段代码导入虚拟机时应该给它们什么样的权限. 任何时候,每一个应用程序都只有一个Policy对象.
    Sun的java1.2平台具体的Policy子类采用在一ASCII策略文件中用上下文无关文法描述安全策略.
    一个策略文件包括了一系列grant子句,每一个grant子句将一些权限授给一个代码来源。

    grant  codesource
    {
        permission1;
        permission2;
    }
    

    保护域(ProtectionDomain)
    当类装载器将类型装入java虚拟机时,它们将为每一个类型指派一个保护域,保护域定义了授予 一段特定的代码的所有权限.装载入java虚拟机的每一个类型都属于一个且仅属于一个保护域.

    访问控制器(AccessController)

    • mplies() 判断一个Permissioin对象的权限,是否隐含(imply)在另一个Permissioin对象的权限中。

    • checkPermission() AccessController的核心方法,这个方法决定一个特定的操作能否被允许. 它自顶向下检查栈,只要它遇到一个没有权限桢,它将抛出一个AccessControlException导常。

    • doPrivileged()有的时候,调用栈较上层(更靠近栈顶)的代码可能希望执行一段代码,而这段代码在调用栈的较下层是不允许执行的。为了使可信的代码执行较不可靠的代码操作(这段不可靠的代码位于调用栈的较下层且没有执行这个操作的权限),AccessController类重载了四个名为doPrivileged()的静态方法.
      1:AccessController会忽略调用doPrivileged()方法的调用者的调用者的权限.
      2:Permission: 权限是用抽象类java.security.Permission的一个子类的实例表示的.
      3:CodeSource: 代码来源,包含代码库URL和签名者.
      4: Permissions: PermissionCollection(权限集合)的子类

      实例:判断用户是否可以读取文件

    import java.io.*;
    
    class UserSecurityManager extends SecurityManager {
    private String passWord;
    private String userName;
    UserSecurityManager(String passWord,String userName) {
        super();
        this.passWord=passWord;
        this.userName=userName;
    }
    private boolean accessOK() {
    	System.out.println("请输入用户名和密码,用逗号隔开");
        BufferedReader dis = new BufferedReader(new InputStreamReader(System.in)); 
        try {
        	String[] value=dis.readLine().split(",");
            if (value[0].equals(userName)&&value[1].equals(passWord))
                return true;
            else
                return false;
        } catch (IOException e) {
            return false;
        }
    }
    public void checkRead(FileDescriptor filedescriptor) {
        if (!accessOK())
            throw new SecurityException("您没有读文件权限");
    }
    public void checkRead(String filename) {
        if (!accessOK())
            throw new SecurityException("您没有读文件权限");
    }
    public void checkRead(String filename, Object executionContext) {
        if (!accessOK())
            throw new SecurityException("您没有读文件权限");
    }
    public void checkWrite(FileDescriptor filedescriptor) {
        if (!accessOK())
            throw new SecurityException("您没有写文件权限!");
    }
    public void checkWrite(String filename) {
        if (!accessOK())
            throw new SecurityException("您没有写文件权限!");
    }
    }
    
    import java.io.*;
    
    public class TestSecurity
    {
       public static void main(String args[])
       {
            try {
                   System.setSecurityManager(new UserSecurityManager("123456","wang"));
                } catch (SecurityException se) {
                    System.out.println("安全管理器启动,您需要输入用户名和密码才能继续操作");
                }
            try {
                BufferedReader fis = new BufferedReader(new FileReader("input.txt"));
                String inputString;
                while ((inputString = fis.readLine()) != null) {
                  System.out.println(inputString);
                }
                fis.close();
            } catch (IOException ioe) {
                System.out.println("I/O 读取文件失败"+"  "+ioe.getMessage());
            }catch(Exception e)
            {
               System.out.println(e.toString());
            }
          
       }
       }
    

    运行结果:
    输入不匹配用户名和密码:

    请输入用户名和密码,用逗号隔开
    zhang,1234
    java.lang.SecurityException: 您没有读文件权限
    

    输入正确的用户名和密码,成功读取文件信息。

    请输入用户名和密码,用逗号隔开
    wang,123456
    hello  word
    
  • 相关阅读:
    springboot(6)-热部署
    springboot(5)-文件上传
    ubuntu修改tomcat使用的jdk
    jstack使用
    HeapAnalyzer如何使用
    查看linux下tomcat使用的jdk版本
    ubuntu-tomcat安装目录
    vi命令
    211java-jdk安装记录
    linux的java安装目录
  • 原文地址:https://www.cnblogs.com/csuwater/p/5420393.html
Copyright © 2011-2022 走看看