Stealer with Clipper Making Rounds in a Mass Campaign
PyPI (Python Package Index) is a widely used repository for software packages for the Python programming language, utilized by developers worldwide for sharing and downloading Python code. Due to the widespread usage of PyPI, it has become a desirable target for Threat Actors (TAs) who aim to attack developers or their projects.
Malicious packages are usually uploaded by disguising them as useful software or by imitating well-known projects by altering their names. In the past, we have encountered multiple instances where attackers have utilized PyPI packages to distribute malware payloads. It has been noted that the frequency of InfoStealers being disseminated through malicious PyPI packages is increasing.
Recently, Cyble Research and Intelligence Labs (CRIL) uncovered multiple malicious Python .whl (Wheel) files that were found to be distributing a new malware named ‘KEKW’. KEKW malware can steal sensitive information from infected systems, as well as perform clipper activities which can lead to the hijacking of cryptocurrency transactions.
Following our investigation, we found that the Python packages under scrutiny were not present in the PyPI repository, indicating that the Python security team had removed the malicious packages. Additionally, CRIL verified with the Python security team on 02-05-2023 and confirmed that they took down the malicious packages within 48 hours of them being uploaded.
Since the malicious packages were taken down quickly, it is impossible to determine the number of people who downloaded them. Nevertheless, we believe that the impact of the incident may have been minimal.
The following packages were observed spreading KEKW malware:
- pythonsqlitetool-1.0.0
- pipsqlpackageV2-1.0.0
- pipfontingaddonsV2-1.0.0
- pythoncryptoaddition-1.0.0
- pipcoloringsextV1-1.0.0
- syssqlitemods-1.0.0
- syscryptographymodsV2-1.0.0
- syscoloringspkg-1.0.0
- syssqlite2toolsV2-1.0.0
- pythoncolorlibV1-1.0.0
- pythoncryptolibV2-1.0.0
- pythonsqlite2toolsV1-1.0.0
- pycolourkits-1.0.0
- pythoncolouringslibV2-3.0.0
- pythoncolouringslibV2-3.0.2
- pythoncolouringslibV2-3.0.1
- pythoncolouringslibV2-1.0.0
- pysqlite3pkgV2-1.0.0
- pyapicolorv2-0.0.1
- pythoncryptlibery-1.0
- pipcryptaddsV2-1.0.0
- sysdatalib-0.0.2
- pysqlilibraryV1-1.0.0
- syscryptlibV2-1.0.0
- syssqlite2package-1.0.0
- pipcolourpackagesV2-1.0.0
- pylibfont-0.1.0
- pythonsqlite2mod-1.0.0
In this campaign, we have identified TAs engaging in financial theft by incorporating clipper functionality and stealer. We have also observed several stealer payloads containing different crypto addresses associated with the TA’s clipper activities. We selected one of the Bitcoin addresses that appeared in over 20 packages and found that there had been a significant increase in transactions for that specific crypto address in the past month.
The figure below provides details of the TAs’ Bitcoin wallet transactions.
Additionally, we discovered that the majority of Python files within the packages contained the domain name “kekwltd[.]ru”. In contrast, only a few contained “blackcap[.]ru”, suggesting that these domains may be linked to the TA.
The figure below shows the TA’s active domain.
Code Analysis
For our analysis, we have taken the Python package “pythonsqlitetool-1.0.0”, which is a .whl file. The .whl file in Python is a wheel distribution format used for packaging and distributing Python software. The .whl file is essentially a ZIP archive containing all the necessary files to install a Python package, including the code, data files, and metadata.
Package name | pythonsqlitetool-1.0.0-py3-none-any.whl |
The .whl file includes an ‘__init__.py’ Python file capable of carrying out malicious actions within the user’s system.
At the beginning of the ‘__init__.py’ Python file, the necessary packages are installed on the victim’s system using the ‘pip install’ command, as shown below.
Functionalities
The primary function of the Python package file includes various capabilities such as anti-debugging, persistence, collecting system information, stealing and grabbing sensitive data from various applications, carrying out clipper activities, and more.
Anti-VM
The Python malware file verifies whether it is running within a controlled environment by examining pre-defined blacklisted hard-coded strings such as username, computer name, system IP address, or hardware ID.
The malware terminates its execution if it identifies a match with any of the strings mentioned below.
Process Termination
The malware checks to determine if any security-related processes are running on the target’s system. If it identifies such processes, it terminates them. The list of security-related process names hardcoded into the script can be seen in the figure below.
Persistence
The KEKW malware sets up a startup entry to achieve persistence, allowing it to execute automatically whenever the victim logs in to their computer using the function startupkekw().
The code snippet below depicts how the malware achieves persistence on the victim’s system.
Collecting System information
The KEKW malware uses the system_information() function to acquire system-related data such as login username, computer name, Windows product key and version, RAM capacity, HWID, IP address, geographic location, Google Maps information, and more.
This is illustrated in the figure below.
Stealer
The primary objective of the malicious Python script is to retrieve sensitive information from the target’s web browser, which includes:
- Passwords
- Cookies
- Histories
- Credit card details
- Tokens
- Profiles
The Python script utilizes multiple separate functions to extract browser data, including files from a range of web browsers such as Google Chrome, Microsoft Edge, Yandex, Brave, Amigo, and others, as shown in the figure below.
The figure below displays the code snippet of the Python function responsible for stealing passwords from the targeted browsers.
The figure below shows the code snippet of the function used to steal the cookies from the browsers.
The code snippet function was used to steal the history from the browsers files in the image below.
The Python function that steals the credit card details from the browsers is illustrated in the figure below.
The image below shows the various browsers targeted by this malware to steal tokens.
Grabber
Additionally, the Python script has functions grabb_mc() and grabb_roblox() to retrieve crucial data, including profiles, account credentials, cookies, cache, and more, from well-known video game platforms like Minecraft and Roblox as shown in the below code snippet.
Clipper
The malware uses the address_swap() function to carry out the clipper activity by replacing the intended cryptocurrency wallet address (as specified in the ‘__config__’ section of the Python file) with the attacker’s cryptocurrency address. This action redirects the victim’s cryptocurrency funds to the attacker’s account.
The below figure shows the code snippet of the clipper function used in the malware Python file.
Capture Screenshot
Moreover, the malware can capture screenshots of the target system by utilizing the steal_screen() function. This action allows the attacker to gain access to sensitive information on the victim’s device, which can be used for malicious purposes by the threat actor.
grabb_GatherAll()
The malware has a function called grabb_GatherAll() that steals passwords and cookies from various popular applications, including Gmail, YouTube, eBay, Netflix, Uber, Outlook, Hotmail, PayPal, TikTok, and others.
The figure below shows the code snippet that steals sensitive information from various popular applications.
Moreover, the malware scans the “Desktop”, “Downloads”, and “Documents” directories for text files with specific names related to sensitive information, such as passwords, login credentials, online transactions, online accounts, wallets, and others. Upon locating these files, it extracts the pertinent data.
The malware is also designed to collect sensitive information from specific applications such as Atomic Wallet, Exodus Wallet, Steam, and NationsGlory.
After obtaining the stolen data, the malware formats it into JSON, compresses it into a ZIP file, and then proceeds to upload the compressed archive to the command and control (C&C) server, as shown below.
- hxxps[:]//kekwltd[.]ru
Conclusion
The group responsible for the KEKW stealer malware has launched a widespread campaign to distribute it. The group targets developers using malicious Python packages, which may also put corporate networks at risk.
The timely action of the Python security team in removing the malicious packages has helped to mitigate the severity of this incident. However, this incident highlights the ongoing threat of supply chain attacks and the importance of remaining vigilant and practicing good cybersecurity hygiene.
Our Recommendations
- Avoid downloading pirated software from warez/torrent websites. The “Hack Tool” on sites such as YouTube, Torrent sites, etc., contains such malware.
- Use strong passwords and enforce multi-factor authentication wherever possible.
- Turn on the automatic software update feature on your computer, mobile, and other connected devices.
- Use a reputed anti-virus and internet security software package on your connected devices, including PC, laptop, and mobile.
- Refrain from opening untrusted links and Email attachments without first verifying their authenticity.
- Educate employees on protecting themselves from threats like phishing/untrusted URLs.
- Block URLs that could be used to spread the malware, e.g., Torrent/Warez.
- Monitor the beacon on the network level to block data exfiltration by malware or TAs.
- Enable Data Loss Prevention (DLP) Solutions on the employees’ systems.
MITRE ATT&CK® Techniques
Tactic | Technique ID | Technique Name |
Execution | T1204 T1047 |
User Execution Windows Management Instrumentation |
Persistence | T1547 | Registry Run Keys / Startup Folder |
Defense Evasion | T1497 T1562 |
Virtualization/Sandbox Evasion Disable or Modify Tools |
Credential Access | T1056 | Credential API Hooking |
Discovery | T1057 T1012 T1082 T1083 |
Process Discovery Query Registry System Information Discovery File and Directory Discovery |
Collection | T1005 | Data from Local System |
Command and Control |
T1071 | Application Layer Protocol |
Indicators of Compromise (IOCs)
Indicators | Indicator Type | Description |
1cc87ac9d9066a9829e4245fd86d4cfc b449b53a50d80ccfaba259ce98424d3f8e4b2c85 7167f3c8f24eebc374ecf4d132fc5e2ff681d208a3b02ab5547f488698d2fffc |
MD5 SHA1 SHA256 |
pipcoloringsextV1-1.0.0-py3-none-any.whl |
76e08229aae953002dce4fe06454e158 ac9ac60bd7bdb43bdd8c728c3aa00434f05d52cc 7485ce031144f1800328b1d538c3eaddd589af85e0323d895e0763f88cb74652 |
MD5 SHA1 SHA256 |
pipcolourpackagesV2-1.0.0-py3-none-any.whl |
d211815d0507aa070b99d5a6c9e3c300 11485ddb88da5dae6e4f9b81f51b32a56565141c 6b951cc544151c6d21ebc2b92dcbeccb03e5c130060fcc671335caead0a19a9e |
MD5 SHA1 SHA256 |
pipcryptaddsV2-1.0.0-py3-none-any.whl |
1e5a4f71632ed0eac001551c6453e2e0 4e2b1fe66e3961f1bbf9805289a9d3d2b3dc0b61 1553712ce5551698f2eeacba0aedaac9d14a6a236d5da1d17e0456a554cf457d |
MD5 SHA1 SHA256 |
pipfontingaddonsV2-1.0.0-py3-none-any.whl |
001beecd74578178013fec56d10724df 228f0d5bb26d7dab58a80bdcb07a7e686e373448 510bc06cfbecf2e1f135bb28b3361558eb529c86d7c65e614d0baea1843db997 |
MD5 SHA1 SHA256 |
pipsqlpackageV2-1.0.0-py3-none-any.whl |
a09e78a04a89e5756c5e5f327758a95e 9ac5ea70a7d8bab4150f670eab33cc41e5375223 744e76feed753102fbb364bdc9cb93faaa63388affa2d30b13c3aa6fe55b0ed9 |
MD5 SHA1 SHA256 |
pyapicolorv2-0.0.1-py3-none-any.whl |
7fa034ccc098809acabfff2fcd4e96ef 2d9d01ea2b76de6d442cd06f1d480593a40962f9 729844cd91c501cd0a5e5bdac6011713f5615b1a2ea408b18551e7f0214f7c47 |
MD5 SHA1 SHA256 |
pycolourkits-1.0.0-py3-none-any.whl |
1629406cbb606fdc4b6a83849f05d12c 6ab46b181445b6dcb52241b02c28b871f913bff9 37fcab1f0926a59c0eead0fbbd597c485e46749ebc5ea177b7ccddfff638cd6a |
MD5 SHA1 SHA256 |
pylibfont-0.1.0-py3-none-any.whl |
d2b0d9bfd1b01f5dfc4cb7f89ffab1ad d0d1a5c2dff40f7a5025e38548bcddfca6dd3863 2d4e38b5fbcdbbdd23a12974c2ee0f0443b27d57b1bebf68a489c1d45dd544f5 |
MD5 SHA1 SHA256 |
pysqlilibraryV1-1.0.0-py3-none-any.whl |
0e2861958488e067d3da724d9baaa42a d3391263ce5b0f516ec1f664692583562215c094 0b4350d79fa4d48942357eac02d1d77d78aa5a2f3b46e0baf802b9bcfc9866dd |
MD5 SHA1 SHA256 |
pysqlite3pkgV2-1.0.0-py3-none-any.whl |
16c67a78cb0f52a8f8fc3091db86b32d b50134c238f77610581524d5280fdc54e9c9aa4b 9f615cc4af941382e81d8327ccfee8aa5f9df06911e04c0687f93643fea176c0 |
MD5 SHA1 SHA256 |
pythoncolorlibV1-1.0.0-py3-none-any.whl |
aec4cc668cb66f5647090efe65e1a878 a1f056b8fb4ba621801c562bcffd5881e3c9879b 74cf526d7f1a9cc9695ebd467e98c494ed2a411cf78140219ceeeb411a2a1aa0 |
MD5 SHA1 SHA256 | pythoncolouringslibV2-1.0.0-py3-none-any.whl |
e84408efb2d1bf3602163c2670de695d 96127e2e7a7e8dd3663dd16e936dd99a86d3b4ed 3d2631c811648f1d127c1a4463b31261ef966353da8c4b5e8fa25ebd78e2644c |
MD5 SHA1 SHA256 |
pythoncolouringslibV2-3.0.0-py3-none-any.whl |
c49f69cc7ee19e5587b383ab46606862 69b3e7acb9ac9c33ca2fb6319995572d23261f41 beb591e7824c255603e240eb944525b8894ff50da8cafd6b13d024b710730f0b |
MD5 SHA1 SHA256 |
pythoncolouringslibV2-3.0.1-py3-none-any.whl |
535e0ec23456420e9e584e56becdde4c 839041e7ee124b2081fa8bbe4f4cc7cc6378865a 63b71c19226c3b6d0cfaa1e5a77593baba711c011d7926ac3fd47848230c02de |
MD5 SHA1 SHA256 |
pythoncolouringslibV2-3.0.2-py3-none-any.whl |
7cba37fe4a82bd727d16140cb00192cb bbfd43cb3d7f7cb0807ff10474ce26d1b85bea61 25b2892e4cff541fcf93ba6b04b047d8e6ef4ad991ebebf2354ad1cb8572e714 |
MD5 SHA1 SHA256 |
pythoncryptlibery-1.0-py3-none-any.whl |
1ba4b9a81a9df9a457e8565e63785b85 f28bb0f3cdb2d1d3181e02df6c908c5a952eb6e1 9ff56e7adf7b56956a0c6e1b9500f0818dafa540da18c23a3eaf1740f6ba00f7 |
MD5 SHA1 SHA256 |
pythoncryptoaddition-1.0.0-py3-none-any.whl |
f13c2c898f2ed318897bca865a9c8069 928a521c6a63da6cdb6a8e3b5dbe204c1e2dfe15 a435a615856ac27b7a004874ed85082a576abe48fb1af2853bd7f6edbf2a938c |
MD5 SHA1 SHA256 |
pythoncryptolibV2-1.0.0-py3-none-any.whl |
7eb67f0591d6ade5ad399dca770a0a6b 9774d70072f8c37a1e610351fd59a47444d1cd06 11e24f6bcf023b570395053d55b5a80126aee80e5ec95b5a85edb435fc503dce |
MD5 SHA1 SHA256 |
pythonsqlite2mod-1.0.0-py3-none-any.whl |
a325f3786acb7806a132684fdfe2112b 67c033b047d858ba06658d9576815e6b9d759d0e 350e2e499cb216273474d872668ce49f495c732166ab20babef02c9dc8962055 |
MD5 SHA1 SHA256 |
pythonsqlite2toolsV1-1.0.0-py3-none-any.whl |
258df1f7a44e343f41a1167e919a3821 2e9ad7aae14b8dae6db1fdcc58c7f449c779ad73 10591a1e39f0d4d39fc9368d5624c0d63c44dbb2d8edb3620d8e02e611c40c49 |
MD5 SHA1 SHA256 |
pythonsqlitetool-1.0.0-py3-none-any.whl |
fd4bd57d2e4e819ce372d5c5d7bba38a 9c44ff1cd30fb5a7690ac38ed38bbcf3247707e0 844d6bb5871f867e9d284c543c38934a4b50c4f5830af097244bbc612e8c3b7f |
MD5 SHA1 SHA256 |
syscoloringspkg-1.0.0-py3-none-any.whl |
e1c8f589963cb0eff93027a7fcfb4b73 1013143dfdb13b44b7f4dfa63e97cf8915339fa7 5cdeae60841c390df95f8c8ad67819746116873ed1e1ae6cc7900c1b74927524 |
MD5 SHA1 SHA256 |
syscryptlibV2-1.0.0-py3-none-any.whl |
38af78324644015f6f607722c128b5d8 ad3e9fa977236ceac8189176ae4d957eead1374f cb6622ad17023ea904a1523d7d1e3f6608a94cdec00f891bccf8735d6e2821cb |
MD5 SHA1 SHA256 |
syscryptographymodsV2-1.0.0-py3-none-any.whl |
cd674b4f5df5c2714205f25097621fae 7cf35adab2ce09ae0fdf629314b86fb2e6d41b53 21e175a3ea87dc5911b2d4cf30d17846cdd28c8bab7f402b20530699108400f4 |
MD5 SHA1 SHA256 |
sysdatalib-0.0.2-py3-none-any.whl |
55145b977e2aade4dd6a1e7f9966266f bec7cd783f07edd2d9c688bdb3678607e3b9516c 75980669d22cf5461ba563fd8a484486e1786d26c653036729b5af8a3e00b061 |
MD5 SHA1 SHA256 |
syssqlite2package-1.0.0-py3-none-any.whl |
cb7c4e1944f852862ec30c2a593582a2 7239e24630b89dd9694c19bab4f4e461b8074d2e 3087728bc04ecc0df07100a297d393d8b94f21245a8a4aa0c4414e5eb84eb8c7 |
MD5 SHA1 SHA256 |
syssqlite2toolsV2-1.0.0-py3-none-any.whl |
e9e052a0448f8da19f75bb1360978505 69f9f8ea73c4cabb80440e091455af3a9a69d478 ba860998a5f7b935461d127b103604e65fd353673a1e571cfca987ac7d5121ef |
MD5 SHA1 SHA256 |
syssqlitemods-1.0.0-py3-none-any.whl |
Related
Source: https://blog.cyble.com/2023/05/03/new-kekw-malware-variant-identified-in-pypi-package-distribution/