中文字幕av专区_日韩电影在线播放_精品国产精品久久一区免费式_av在线免费观看网站

溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

Java中怎么實現RASP機制

發布時間:2021-08-07 14:44:32 來源:億速云 閱讀:137 作者:Leah 欄目:編程語言

這篇文章將為大家詳細講解有關Java中怎么實現RASP機制,文章內容質量較高,因此小編分享給大家做個參考,希望大家閱讀完這篇文章后對相關知識有一定的了解。

RSAP

RASP是Gartner公司提出的一個概念,稱:程序不應該依賴于外部組件進行運行時保護,而應該自身擁有運行時環境保護機制;

RASP就是運行時應用自我保護(Runtime application self-protection)的縮寫,正如RASP字面意思一樣,這是運行在運行時的一種防護技能;也就是說RASP能夠在程序運行期間實施自我保護,監控與過濾有害信息,還能夠擁結合程序的當前上下文實施精確、實時的防護;

Java中的RASP

不嚴格來說Java是半編譯、半解釋型語言,我們也都知道Java中也有運行時(Runtime)那Java的運行時在哪呢?

不急,我們先看看Java從編譯到運行的流程圖;

上圖的流程為:Java編譯程序如Javac編譯.java源碼文件,生成Java字節碼文件.class,接著.class文件進入JVM中解釋執行; 從中我們可以看到Java的最后執行階段是在JVM中,也就可以說Runtime運行時是JVM的重要組成部分;除此之外我們還發現

Java中實現RASP的幾個關鍵點:

1、 我們的防護程序必須能夠分析、修改java的.class文件;

2、 必須在JVM解釋執行.class文件時進行注入(Java Runtime);

通過上面的分析我們知道了要實現Java的RASP所要具備的能力,然后我們發現在Java中有Javassist、與ASM可以實現對Java字節碼的修改;有了修改.class字節碼文件的技能,還需要能夠在Java運行期間注入我們的防護程序,通過上面我們發現Java運行時是發生在JVM中,通過查找相關資料與JVM參數發現在JVM參數中有-javaagent參數配置Java代理可以在 運行時注入我們的防護程序;

Java RASP實現

在上面的分析中我們發現只要在JVM的-javaagent參數 中配置我們的保護程序,就能夠輕松實現Java的RASP;

Java代理程序入口類需要有名為premain的靜態方法 ,還需要在jar的META-INF/MAINIFEST.MF文件中包含 Premain-Class配置,下面是RASP保護程序的入口類;

JavaRASPApp:

/** * @author linx * @date 2017-06-25*/public class JavaRASPApp { public static void premain(String agentArgs, Instrumentation instru) throws ClassNotFoundException, UnmodifiableClassException {  System.out.println("premain");  instru.addTransformer(new ClassTransformer()); }}

ClassTransformer類實現了Java的代理程序機制提供的ClassFileTransformer接口 ,能夠在運行時(Runtime)對類的字節碼進行替換與修改;

ClassTransformer也很簡單,只有一個實現方法:transform,此方法中可以獲取得到ClassLoader、className、classfileBuffer等,分別為類加載器、類名、字節碼 ;

此時我們可以在transform方法中做文章,實現我們的防護程序;

/** * @author linxin * @version v1.0 *     Copyright (c) 2017 by linx * @date 2017/6/23.*/ public class ClassTransformer implements ClassFileTransformer { public byte[] transform(ClassLoader loader, String className, Class<?> classBeingRedefined, ProtectionDomain protectionDomain, byte[] classfileBuffer){  byte[] transformeredByteCode = classfileBuffer;  try {    if (className.equals("co/solinx/demo/Test")) {      System.out.println(String.format("transform start %s",className));      ClassReader reader = new ClassReader(classfileBuffer);      ClassWriter writer = new ClassWriter(ClassWriter.COMPUTE_MAXS);      ClassVisitor classVisitor = (ClassVisitor) createVisitorIns("co.solinx.demo.visitor.TestVisitor", writer, className);      reader.accept(classVisitor, ClassReader.EXPAND_FRAMES);      transformeredByteCode = writer.toByteArray();     }  } catch (Exception e) {    e.printStackTrace();  }catch (Throwable t){    t.printStackTrace();  }  return transformeredByteCode;} public Object createVisitorIns(final String name, ClassVisitor cv, String className)    throws NoSuchMethodException, InstantiationException, IllegalAccessException, InvocationTargetException, ClassNotFoundException {  Constructor<?> ctor = Class.forName(name).getDeclaredConstructor(new Class[]{ClassVisitor.class, String.class});  ctor.setAccessible(true);  return ctor.newInstance(new Object[]{cv, className}); }}

可以看到我們在transform方法中co/solinx/demo/Test類進行攔截,并通過ASM修改字節碼注入我們的保護邏輯,下面代碼是TestVisitorAdapter類中的onMethodEnter方法實現了通過ASM調用攔截器,拋出異常的字節碼;

@Overrideprotected void onMethodEnter() {   mv.visitTypeInsn(NEW,"co/solinx/demo/filter/SqlFilter");  mv.visitInsn(DUP);  mv.visitMethodInsn(INVOKESPECIAL,"co/solinx/demo/filter/SqlFilter","<init>","()V",false);  mv.visitVarInsn(ASTORE,2);  mv.visitVarInsn(ALOAD,2);  mv.visitVarInsn(ALOAD,1);  mv.visitMethodInsn(INVOKEVIRTUAL,"co/solinx/demo/filter/SqlFilter", "filter","(Ljava/lang/Object;)Z",false);  Label label = new Label();  /**   * IFEQ filter返回值也就是棧頂int型數值等于true時跳轉,拋出異常   */  mv.visitJumpInsn(IFEQ, label);   mv.visitTypeInsn(NEW, "java/sql/SQLException");  mv.visitInsn(DUP);  mv.visitLdcInsn("invalid sql because of security check");  mv.visitMethodInsn(INVOKESPECIAL, "java/sql/SQLException", "<init>", "(Ljava/lang/String;)V", false);  mv.visitInsn(ATHROW);  mv.visitLabel(label);  /**   * 必須要調該方法,手動設置Stack Map Table,否則會有 java.lang.VerifyError: Expecting a stackmap frame at branch target 26異常   * 在jdk1.7中可以使用JVM參數-UseSplitVerifier,關掉class驗證,但jdk1.8中該參數已經去掉,所以要在1.8中運行必須調用該方法;   */  mv.visitFrame(Opcodes.F_SAME, 0, null, 0, null); }

SqlFilter攔截類:

public class SqlFilter {public boolean filter(Object sql){  boolean ret=false;  System.out.println(String.format("sql filter : %s ",sql));  if(sql.toString().contains("1=1")){    ret=true;  }  return ret;}}

TestVisitorAdapter類中的onMethodEnter方法中通過調用filter攔截器,返回true就是被攔截了,拋出異常,否則放行;至此一個簡單的JAVA RASP demo就完成了; 通過后面的方式即可使用我們的RASP程序:java -javaagent:respjar-1.0-SNAPSHOT.jar app.jar;

關于Java中怎么實現RASP機制就分享到這里了,希望以上內容可以對大家有一定的幫助,可以學到更多知識。如果覺得文章不錯,可以把它分享出去讓更多的人看到。

向AI問一下細節

免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。

AI

琼结县| 娱乐| 德昌县| 磐石市| 景洪市| 双牌县| 卢湾区| 西青区| 邵武市| 旬阳县| 保德县| 枝江市| 伽师县| 甘南县| 桂阳县| 湘潭县| 巴东县| 株洲县| 宿松县| 长宁区| 长海县| 囊谦县| 旬阳县| 西峡县| 宁波市| 兴海县| 资源县| 甘南县| 南部县| 南平市| 仁怀市| 历史| 三亚市| 济宁市| 镶黄旗| 富宁县| 莱西市| 久治县| 莲花县| 丽江市| 大厂|