# Enumeration

워드프레스에서 기본적인 설정을 사용한다면 다음의 방법들을 사용하여 사용자 계정 목록을 열거하는 것이 가능합니다.

### 로그인 응답 차이

기본적으로 워드프레스 기반의 사이트는 최상위 경로에서 wp-admin으로 접근 시 관리자 페이지로 접근할 수 있고, 존재하는 계정과 존재하지 않는 계정을 로그인 응답으로부터 구분할 수 있습니다.

<div><figure><img src="/files/DV6XFALBsPpU9GVzyjwu" alt=""><figcaption><p>존재하지 않는 계정</p></figcaption></figure> <figure><img src="/files/N0hU64yasNiycFM4PhNr" alt=""><figcaption><p>존재하는 계정</p></figcaption></figure></div>

### Rest API

인가되지 않은 사용자로부터 Rest API 요청에 따른 응답이 되는 워드프레스 기본 설정의 경우 워드프레스 서버의 최상위 경로에서 `?rest_route=/wp/v2/users` , `/wp-json/wp/v2/users` , `/wp-json/wp/v2/users?per_page=100` 엔드포인트로 접근하면 slug 키 값으로 사용자 계정 이름을 반환합니다.

<figure><img src="/files/SePfQdrNZavaD7JPovn7" alt=""><figcaption><p>Rest API 요청</p></figcaption></figure>

### 게시글 작성자 조회

워드프레스에서 게시글을 1회라도 작성한 사용자는 작성자를 검색하는 파라미터에 대한 요청을 통해 식별할 수 있습니다. 이 값은 게시글을 작성한 순서대로 인덱스 값이 올라갑니다.

<figure><img src="/files/Ezp5QlIuOS2bk8VSKgTo" alt=""><figcaption><p>첫번째 사용자 조회</p></figcaption></figure>

<figure><img src="/files/S5SXzLJHKL7UdwIqrpC7" alt=""><figcaption><p>없는 사용자 조회</p></figcaption></figure>

위에서 언급한 방법들은 모두 다른 방식으로 사용자 목록을 열거할 수 있기 때문에 버전이나 서버 설정 등에 따른 반응의 차이에 따라 맞는 방법을 선택해야 합니다.

### 무차별 대입 공격

xmlrpc는 2000년대 초 Rest API가 보급화되기 이전 서로 다른 언어와 시스템으로 작성한 데이터를 주고받기 위해 제공하던 서비스입니다.

현재는 워드프레스에서 xmlrpc 기능을 사용할 일이 거의 존재하지 않아 언제 사라져도 이상하지 않으며, 이 기능에서 보안 취약점이 발생할 수 있기 때문에 비활성화 하거나 파일을 삭제하는 것을 권장하기도 합니다.

이 파일이 존재하거나 보안 플러그인을 사용하지 않을 경우 정상적으로 이용할 수 있으며, 엔드포인트로 접근함에 따라 그 여부를 확인할 수 있습니다.

<figure><img src="/files/eZSGRv8Q2JGmuuwZlx1l" alt=""><figcaption><p>xmlrpc.php 존재 여부 확인</p></figcaption></figure>

xmlrpc.php는 POST 요청만을 허용하기 때문에 상기와 같은 405 오류가 반환된다면 양성 반응입니다.

xmlrpc에서는 워드프레스의 함수들을 XML 방식으로 요청하여 호출할 수 있는데, xp.getUsersBlogs는 사용자의 계정정보를 받아서 해당 사용자의 정보에 대한 구조체를 반환하는 함수입니다.

<figure><img src="/files/ZKmEu4yeJoj94evfqWzJ" alt=""><figcaption></figcaption></figure>

따라서 공격자는 xmlrpc.php의 POST 요청으로 사용자 계정정보를 무작위로 대입하여 xp.getUsersBlogs 함수를 호출하고, 이 함수의 호출 결과가 있다면 해당 계정이 유효함을 추론할 수 있습니다.

{% code title="브루트포스 XML 코드" %}

```xml
<?xml version="1.0"?>
<methodCall>
  <methodName>wp.getUsersBlogs</methodName>
  <params>
    <param><value><string>admin</string></value></param>
    <param><value><string>password123</string></value></param>
  </params>
</methodCall>
```

{% endcode %}

<div><figure><img src="/files/gG7BGkePtFW9zJctai7D" alt=""><figcaption><p>로그인 성공 응답</p></figcaption></figure> <figure><img src="/files/MRyXiF4rA25ZYa2H6Jk1" alt=""><figcaption><p>로그인 실패 응답</p></figcaption></figure></div>

## References

{% embed url="<https://anotherark.com/438/>" %}

{% embed url="<https://velog.io/@0x6a0x640x68/Report-WordPress-xmlrpc-%EC%B7%A8%EC%95%BD%EC%A0%90>" %}

{% embed url="<https://codex.wordpress.org/XML-RPC_wp?utm_source=chatgpt.com>" %}


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://www.pentestwiki.com/etc/wordpress/enumeration.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
