代码漏洞

本文详细介绍了十个常见的代码安全漏洞,包括SQL注入、XML外部实体注入、重定向漏洞等,逐一分析风险并提出相应的安全建议和解决方法,旨在提升系统的安全性。

这里是我在工作中遇到过的一些存在而且不会注意的编码漏洞, 会造成系统的不安全性, 这里将会从漏洞风险由高到低一一介绍总结以下

1. SQL 注入漏洞 (高等风险)
  • 风险分析

    • SQL 注入式一种数据库攻击手段, 攻击者通过向应用程序提交恶意代码来改变原来 SQL 语句的含义, 进而执行任意 SQL 命令, 达到入侵数据库乃至操作系统的目的
  • 安全建议

    • 在入口文件处添加 SQL 过滤器, 直接拦截过滤特殊字符
  • 处理方式

    • 增加全局过滤器
    • 在 配置文件 web.xml 中注册
    import java.io.IOException;
    import java.util.Enumeration;
    import javax.servlet.FilterChain;
    import javax.servlet.FilterConfig;
    import javax.servlet.ServletException;
    import javax.servlet.ServletRequest;
    import javax.servlet.ServletResponse;
    import javax.servlet.http.HttpServletRequest;
    import javax.servlet.Filter;
    import javax.servlet.http.HttpServlet;
    /**
     * @Author: 九千七
     * @date: 2021/2/3 17:12
     * @description: 增加 SQL 注入过滤器, 过滤所有请求
     */
    /*
     *  通过过滤器过滤SQL注入特殊字符
     */
    @SuppressWarnings({"rawtypes", "JavaDoc"})
    public  class InjectFilter extends HttpServlet implements Filter {
    
        private static final String failPage = "ErrorHandle.jsp";     //发生注入时,跳转页面, 此处为你自己项目中定义的错误界面
    
        public void doFilter(ServletRequest request,ServletResponse response,
                             FilterChain filterchain)throws IOException, ServletException {
            //判断是否有注入攻击字符
            HttpServletRequest req = (HttpServletRequest) request;
            String inj = injectInput(req);
            if (!inj.equals("")) {
                request.getRequestDispatcher(failPage).forward(request, response);
            } else {
                // 传递控制到下一个过滤器
                filterchain.doFilter(request, response);
            }
        }
        
        /**
         * 判断request中是否含有注入攻击字符
         * @param request
         * @return inj
         */
        public String injectInput(ServletRequest request) {
    
            Enumeration e = request.getParameterNames();
            String attributeName;
            String[] attributeValues;
            String inj = "";
            while (e.hasMoreElements()) {
                attributeName = (String)e.nextElement();
                //不对密码信息进行过滤,一般密码中可以包含特殊字符
                if(attributeName.equalsIgnoreCase("userPassword")||attributeName.equalsIgnoreCase("confirmPassword")|| attributeName.equalsIgnoreCase("PASSWORD")
                        ||attributeName.equalsIgnoreCase("PASSWORD2")||attributeName.equalsIgnoreCase("valiPassword")){
                    continue;
                }
                attributeValues = request.getParameterValues(attributeName);
                for(String attributeValue : attributeValues) {
    
                    if (attributeValue == null || attributeValue.equals(""))
                        continue;
                    inj = injectChar(attributeValue);
    
                    if (!inj.equals("")) {
                        return inj;
                    }
                }
            }
            return inj;
        }
        
        /**
         * 判断字符串中是否含有注入攻击字符
         * @param str
         * @return s
         */
        public String injectChar(String str) {
            String inj_str = ") * % < > & \' = or ";
            String[] inj_stra = inj_str.split(" ");
    
            for (String s : inj_stra) {
                if (str.contains(s)) {
                    return s;
                }
            }
            return "";
        }
        
        @Override
        public void init(FilterConfig filterConfig){
            // TODO Auto-generated method stub
            // System.out.println("----注入过滤器初始化----");
        }
    }
    
    <filter>
    		<filter-name>InjectFilter</filter-name>
    		<filter-class>com.ztesoft.resmaster.sys.InjectFilter</filter-class>
    	</filter>
    	
    	<filter-mapping>
    		<filter-name>InjectFilter</filter-name>
    		<!--“/*”表示拦截所有的请求 -->
    		<url-pattern>/*</url-pattern>
    	</filter-mapping>
    
2. XML 外部实体注入 (高等风险)
  • 漏洞分析

    • 通过本次代码安全审计发现,系统允许引用外部实体易造成允许引用xml外部实体注入
  • 安全建议

    • 使用开发语言提供的禁用外部实体的方法:

      DocumentBuilderFactory dbf =DocumentBuilderFactory.newInstance();
      dbf.setExpandEntityReferences(false);
      
    • 过滤用户提交的XML数据,关键词:<!DOCTYPE 和 <!ENTITY,或者,SYSTEM 和 PUBLIC

  • 解决方法

    • DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
      		factory.setExpandEntityReferences(false);
              DocumentBuilder builder = factory.newDocumentBuilder();
              org.w3c.dom.Document doc = builder.parse(new InputSource(new StringReader(inxml)));   
              org.w3c.dom.Element root = doc.getDocumentElement();   
      
3 . 重定向漏洞 (高等风险)
  • 漏洞分析
    • 应用程序允许未验证的用户输入控制重定向中的URL,可能会导致攻击者发动钓鱼攻击
  • 安全建议
    • 防止重定向漏洞的方法是创建一份合法URL列表,用户只能从中进行选择,进行重定向操作
  • 解决方法
    • [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-auvGgBEu-1615174430560)(C:\Users\Administrator\AppData\Roaming\Typora\typora-user-images\image-20210219165202870.png)]
4 . 硬编码 (中等风险)
  • 漏洞分析

    • 程序中采用硬编码方式处理密码,一方面会降低系统安全性,另一方面不易于程序维护
  • 安全建议

    • 程序中所需密码应从配置文件中获取经过加密的密码值
  • 解决方法

    • 可以自己增加一个加密与解密函数, 然后将密码全部转换为加密的数据
    • 这里提供一个简单的加密与解密函数
    /**
     * @author: 九千七
     * @date: 2021/1/29 10:09
     * @description:
     */
    public class DealPWD {
        public static String encrypt(String strpasswd) {
            StringBuffer ls_decrypt = new StringBuffer();
            //String ls_seed = "ZXT10LSZTESOFTRESMASTER";
            // 2010-05-21 modified by wanggp 密钥加长到64位,支持64位数据加密
            String ls_seed = "ZXT10LSZTESOFTRESMASTERBUSINESSOPERATIONSUPPORTSYSTEMRESMASTER30";
            for (int i = 0; i < strpasswd.length(); i++) {
                int j = strpasswd.charAt(i) + ls_seed.charAt(i) - 64;
                if (j >= 95) {
                    j = j - 95;
                }
                ls_decrypt.append(String.valueOf((char) (j + 32)));
            }
            return ls_decrypt.toString();
        }
        /**解密函数
         *
         * @author
         * @get()
         * @return String
         *
         */
        public static String decrypt(String strpasswd) {
            StringBuffer ls_decrypt = new StringBuffer();
            //String ls_seed = "ZXT10LSZTESOFTRESMASTER";
            String ls_seed = "ZXT10LSZTESOFTRESMASTERBUSINESSOPERATIONSUPPORTSYSTEMRESMASTER30"; // 2010-05-21 modified by wanggp 密钥加长到64位,支持64位数据加密
            for (int i = 0; i < strpasswd.length(); i++) {
                int j = strpasswd.charAt(i) - ls_seed.charAt(i) + 95;
                if (j >= 95) {
                    j = j - 95;
                }
                ls_decrypt.append(String.valueOf((char) (j + 32)));
            }
            return ls_decrypt.toString();
        }
    }
    
5. 明文密码 (中等风险)
  • 漏洞分析
    • 配置文件中采用明文存储密码,将会降低系统安全性
  • 安全建议
    • 配置文件中的密码应进行加密存储
  • 解决方法
    • 即先采用自己的加密函数对配置文件中的密码进行加密, 然后在调用的地方使用解密函数进行解密, 解决了明文密码的漏洞
6. 不安全的随机数 (中等风险)
  • 漏洞分析
    • Java API 中提供了 java.util.Random 类实现 PRNG(),该 PRNG 是可移植和可重复的,如果两个 java.util.Random 类的实例使用相同的种子,会在所有 Java 实现中生成相同的数值序列
  • 安全建议
    • 在安全性要求较高的应用中,应使用更安全的随机数生成器,如java.security.SecureRandom类
  • 解决方法
7. 硬编码文件分隔符 (中)
  • 漏洞分析

    • 系统存在硬编码文件分隔符
    • 不同的操作系统使用不同的字符作为文件分隔符。例如,Windows系统使用"",而UNIX系统则使用"/"。应用程序需要在不同的平台上运行时,使用硬编码文件分隔符会导致应用程序逻辑执行错误,并有可能导致拒绝服务。
  • 安全建议

    • 不应使用硬编码文件分隔符,而应使用语言库提供的独立于平台的API。

      例如:针对示例代码的修改方法是:

      File file = new File(directoryName + File.separator + fileName);

  • 解决方法

    • File file = new File(directoryName + File.separator + fileName);
8. 不安全的哈希算法 (中等风险)
  • 漏洞分析
    • 在安全性要求较高的系统中,不应使用被业界公认的不安全的哈希算法(如MD2、MD4、MD5、SHA、SHA1等)来保证数据的完整性
  • 安全建议
    • 在安全性要求较高的系统中,应采用散列值>=224比特的SHA系列算法(如SHA-224、SHA-256、SHA-384和SHA-512)来保证敏感数据的完整性
  • 解决方法
    • 改用非对称加密处理数据
9. 路径篡改 (中等风险)
  • 漏洞分析

    • 可操作系统中可控变量来进行获取特定权限或指令操作等危险行为
  • 安全建议

    • 对用户输入的数据进行全面安全检查或过滤,尤其注意检查是否包含HTML特殊字符。这些检查或过滤必须在服务器端完成,建议过滤的常见危险字符如下:

      |(竖线符号)

      & (& 符号)

      ;(分号)

      $(美元符号)

      %(百分比符号)

      @(at 符号)

      '(单引号)

      "(引号)

      '(反斜杠转义单引号)

      "(反斜杠转义引号)

      <>(尖括号)

      ()(括号)

      +(加号)

      CR(回车符,ASCII 0x0d)

      LF(换行,ASCII 0x0a)

      ,(逗号)

      \(反斜杠)

      Eval方法

      Document

      Cookie

      Javascript

      Script

      onerror。

  • 解决方法

10. 无用的 main 方法 (低等风险)
  • 安全建议
    • 系统中存在无用的测试文件和方法,恶意攻击者可以利用这些信息为进一步攻击内网系统提供帮助
  • 解决方法
    • 建议删除测试文件和方法
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

§九千七§

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值