Pancake's AI blog

Made by AI and reviewed by slaves^Whumans

Technical Analysis of BadPack Malware’s ZIP Header Exploitation Techniques

Generated by Perplexity’s Research

Executive Summary

Recent cybersecurity research has uncovered sophisticated exploitation techniques in BadPack malware targeting Android’s APK file structure12. This advanced persistent threat leverages deliberate manipulation of ZIP archive headers to bypass traditional malware analysis tools while maintaining functionality on Android devices. By creating intentional mismatches between local file headers and central directory headers within APK files, attackers achieve dual objectives: 1) preventing static analysis of critical components like AndroidManifest.xml, and 2) ensuring successful execution on victim devices. Palo Alto Networks’ Unit 42 researchers identified nearly 9,200 BadPack samples between June 2023-June 2024, demonstrating widespread adoption of these techniques by banking Trojans like BianLian and Cerberus2. This report provides comprehensive technical analysis of the ZIP header manipulation mechanics, reverse engineering challenges, and mitigation strategies.

APK File Structure Fundamentals

ZIP Archive Composition

Android Application Packages (APKs) utilize standard ZIP file format with specialized structural requirements:

[Local File Header 1]
[File Data 1]
[Local File Header 2] 
[File Data 2]
...
[Central Directory Header 1]
[Central Directory Header 2]
[End of Central Directory Record]

Critical components include:

The hexadecimal signature 50 4B 03 04 (PK) marks local headers, while central directories use 50 4B 01 02 (PK)2.

Header Field Criticality

Key fields vulnerable to BadPack manipulation:

Field Name  Offset  Size    Purpose
Compression Method  0x08    2B  0=Store, 8=Deflate
Compressed Size 0x12    4B  Size after compression
Uncompressed Size   0x16    4B  Original file size
File Name Length    0x1A    2B  Length of subsequent filename
Extra Field Length  0x1C    2B  Length of additional metadata

Listing 1: Critical ZIP header fields targeted by BadPack2 BadPack Exploitation Techniques Header Mismatch Methodology BadPack operators exploit differential parsing between analysis tools and Android runtime: Analysis Tools (Apktool/Jadx): Validate consistency between local/central headers Android Runtime: Primarily utilizes central directory headers, ignoring local discrepancies This allows malicious APKs to: Pass Android installation checks (central headers valid) Crash analysis tools (header mismatches trigger parsing errors) Technical Implementation Variants Method 1: Valid Compression with Invalid Sizes

Local Header:
  Compression Method: 0x0000 (Store)
  Compressed Size:    0x0000A1B0 (41392) 
  Uncompressed Size:  0x0000A1B0 (41392)

Central Directory:  
  Compression Method: 0x0000 (Store)
  Compressed Size:    0x0000A1B0 (41392)
  Uncompressed Size:  0x0000A1B0 (41392)
Actual compressed data size: 0x0000A1B1 (41393)
Analysis tools crash on size validation failure, while Android uses central directory values2.
Method 2: Compression Method Spoofing
text
Local Header:
  Compression Method: 0x0008 (Deflate)
  Compressed Size:    0x00004370 (17264)
  Uncompressed Size:  0x00004370 (17264)  

Central Directory:
  Compression Method: 0x0000 (Store)  
  Compressed Size:    0x00004370 (17264)
  Uncompressed Size:  0x00004370 (17264)

Here, local header claims Deflate compression while central directory specifies Store. Android honors central directory, while tools attempt Deflate decompression on improperly compressed data2.

Method 3: Header Field Corruption

Local Header:
  Compression Method: 0xFFFF (Invalid)  
  Compressed Size:    0xDEADBEEF 
  Uncompressed Size:  0xCAFEBABE

Central Directory:
  Compression Method: 0x0000 (Store)
  Compressed Size:    0x0002A1F0 (172272)
  Uncompressed Size:  0x0002A1F0 (172272) 
Invalid local fields cause analysis tool failures, while Android's runtime ignores them.

Android Runtime Handling

Code-Level Analysis

Critical code paths in Android’s PackageParser class demonstrate header processing differences:

public class PackageParser {
    public Package parsePackage(File packageFile, int flags) throws PackageParserException {
        
        // Retrieve central directory entry
        ZipEntry manifestEntry = zipFile.getEntry("AndroidManifest.xml");
        
        if (manifestEntry.getMethod() == ZipEntry.DEFLATED) {
            InputStream is = zipFile.getInputStream(manifestEntry);
            // Decompress using Deflate
        } else {
            // Read uncompressed data directly
            int size = (int) manifestEntry.getSize(); 
            byte[] data = new byte[size];
            // Read from offset with STORE method
        }
        
        // Parse manifest XML
        return parsePackage(data); 
    }
}

Listing 2: Simplified Android manifest parsing logic2

Key behavioral differences:

Relies solely on central directory’s getMethod() and getSize() No validation against local header values Invalid local headers don’t affect runtime extraction Installation Process Experimentation Unit42 researchers validated this behavior through controlled APK modifications:

Valid APK Installation

$ adb install original.apk
Success
Modified Central Directory Compression
bash
$ hexedit modified.apk
# Change central directory compression from 0x0008 → 0x0000

$ adb install modified.apk 
Failure [INSTALL_PARSE_FAILED_UNEXPECTED_EXCEPTION: Corrupt XML]

This demonstrates Android’s dependency on valid central directory metadata2.

Reverse Engineering Challenges

Analysis Tool Limitations

Traditional Android reverse engineering tools fail due to strict ZIP specification adherence:

Tool Failure Mode BadPack Impact
Apktool Header validation exceptions AndroidManifest extraction
Jadx CRC/Size mismatches Decompilation errors
unzip Invalid compression methods Extraction aborted
apksigner Header integrity checks Verification failures

apkInspector Success Factors

The open-source apkInspector tool succeeds through:

Implementation excerpt:

def fix_local_headers(apk_path):
    with open(apk_path, 'r+b') as f:
        # Parse central directory
        cdir = read_central_directory(f)  
        
        # Overwrite local headers
        for entry in cdir.entries:
            f.seek(entry.local_header_offset)
            write_local_header(f, entry)  # Use central dir values
            
def extract_manifest(apk_path):
    fix_local_headers(apk_path)
    # Proceed with standard extraction

Listing 3: Header normalization approach1

Mitigation Strategies

Detection Improvements in Header Consistency Checks:

def detect_badpack(apk):
    for entry in apk.infolist():
        local = entry.header_offset
        central = entry.central_offset
        if local.compression != central.compression:
            return True
        if local.compress_size != central.compress_size:
            return True 
    return False

Entropy Analysis: Compressed vs. stored data entropy discrepancies

Structural Signatures:

Operational Practices

  1. Installation Sources: Restrict to Google Play Store
  2. Permission Auditing:
aapt dump permissions infected.apk
# Check for excessive permissions
  1. Runtime Monitoring:

Conclusion

BadPack represents a significant evolution in Android malware obfuscation, exploiting fundamental differences between ZIP specification validation and runtime pragmatism. By understanding the technical nuances of local/central header mismatches, security teams can develop better detection mechanisms and analysis tools. The ongoing arms race between malware authors and defenders necessitates continuous updates to APK parsing implementations, emphasizing the need for:

  1. Adaptive Analysis Tools: Tolerant of non-compliant ZIP structures
  2. Behavioral Detection: Beyond static header analysis
  3. Platform Hardening: Android runtime validation improvements

Future research directions should explore machine learning models trained on raw APK bytes to detect structural anomalies indicative of BadPack and similar techniques.


source on github // --pancake