Jenkins
Last updated
Last updated
Jenkins is an open source automation server. It helps automate the parts of software development related to building, testing, and deploying, facilitating continuous integration, and continuous delivery. It is a server-based system that runs in servlet containers such as Apache Tomcat
Not a lot is recorded with default Jenkins logs.
Docker Logs:
var/snap/docker/common/var-lib-docker/volumes/13e15a1c49a2cccb9acf4dc096b7bd380de8bba800709ce7d15a92b5f23dfb97/_data/log
Log Recorders:
/var/jenkins_home/logs
Default Locations:
/var/jenkins_home/
/var/jenkins_home/config.xml
/var/jenkins_home/credentials.xml
/var/jenkins_home/jobs/JOBNAME
The config file will tell you everything you need to know about a Jenkins instance:
If anonymous access it turned on
What type of user access control is enabled
Every user can do anything (including anonymous users).
Only logged in user's have full access to everything.
Only certain users can perform certain tasks (role-based and matrix based access).
What type of authentication is allowed:
LDAP
Active Directory
Jenkins' own user database
Unix users/groups
Where the Workspace and Builds directory are located.
Authorization Strategy, which determines who has access to what.
If this is disabled, Jenkins will allow authentication without providing credentials. This will allow any person to access Jenkins with full access.
Security Realm, which determines users and their passwords, as well as what groups the users belong to. In the below snippet, Active Directory users are allowed to access Jenkins.
File requires root access to read.
Jenkins service account is created on Jenkins install and does not have root access typically.
To decrypt passwords in Script Console, the values in the <password> fields must be provided.
Script console can execute Groovy based scripts and run commands on the OS. This can be leveraged for post compromise actions like lateral movement, credential theft, execution, and persistence.
Outputs or commands are not logged by default.
Access is controlled by the Overall Administrator permission in Jenkins.
Any normal type of post exploitation action that you can think of can be performed through the Jenkins Script Console.
Persistence
Setup scheduled tasks or services (Depends on OS).
Lateral Movement
Drop a beacon or establish a connection with a C2 and then move deeper into network.
Decrypt credentials and move into cloud/GitHub environment.
Execution of any command available.
Recon commands.
Creating users.
Adding users to groups.
Credential Dumping:
Executing Mimikatz.
Reading files that contain plaintext passwords.
Decrypting Jenkins credentials.
Users can read stored Jenkins credentials and decrypt them from the Script Console.
There are many types of credentials stored in Jenkins:
GitHub Tokens.
SSH keys and usernames/passwords.
Active Directory usernames/passwords.
Cloud credentials.
To decrypt the credentials, the user must provide the encrypted password found in credentials.xml in the <password> field.
Whenever a user executes commands from Script Console, it should be spawning from a Java process. This makes hunting for post exploitation activities from a threat actor detectable.
Suspicious processes should be spawning from:
Linux:
usr/bin/java
Windows:
java.exe
If Script Console is not accessible, jobs can instead be used to execute code on the underlying OS.
Jobs can be created to execute shell commands or a Windows batch commands (depending on OS). In the event that the user's permissions don't allow them to create a job, existing jobs may also be reconfigured as a means of executing shell commands.
In the Linux version of Jenkins, build instructions will be written and executed from the /tmp folder with the Jenkins naming convention. These files are immediately deleted after execution, so carving for them will be your best shot at finding them.
/tmp/jenkins17741847249180715264.sh
There will be no artifacts related to the shell commands in the workspaces directory.
/var/jenkins_home/workspace/test
The config.xml file for jobs can be used to find any shell commands that the TA might've added.
/var/jenkins_home/jobs/test/config.xml
If anonymous access is enabled, the user who created the Freestyle project or initiated the build will not be known.
/var/jenkins_home/jobs/test/builds/3/build.xml
The Script Console output will be stored in a log file after a successful build.
/var/jenkins_home/jobs/<Build name>/builds/<Build #>/log
Users with access to the build history can pilfer through these in order to find sensitive information:
GitHub Tokens
Secrets/passwords
Files in the UserContent directory are not subject to any access controls beyond requiring Overall/Read access.
This makes it a viable area for storing various things:
Script Console output.
Console/secrets can be redirected to this folder after each build.
Storing webshells.
Files can be accessed by navigating to the following URL:
http://jenkins/userContent/file.txt
This directory should be checked to ensure nothing nefarious has been written to it.
/var/jenkins_home/UserContent
C:/Program Files (x86)/Jenkins/userContent
The Active Directory Plugin allows AD users to authenticate to Jenkins and also allows anonymous read access as an option.
By default, failed authentications will be logged within the following locations:
Jenkins logs
4625 Event ID
4625:
By default, successful logins will ONLY be logged on the authenticating server (DC) and not in Jenkins.
In both successful and failed logins, the source IP is the Jenkins server and the workstation name is the authenticating server (DC).
The following event IDs will be logged on the DC for any successful authentication:
4624 An account was successfully logged on.
4628 A logon was attempted using explicit credentials.
4634 An account was logged off.
4627 Group membership information.
4776 The computer attempted to validate the credentials for an account.
4624:
4628:
4634:
4776:
Anonymous user access is only logged in Jenkins whenever they navigate to a page without permissions.
Because the URL is tracked, these log entries can be used to track:
Failed script execution attempts.
Exploitation attempts.
Recon activity from threat actor.
If Jenkins is exposed to the internet with anonymous read access, anyone can view the Jenkins console output of executed jobs and harvest credentials that may be exposed in command lines.
This is a very common technique and many attackers will just download the console output of every project in an exposed Jenkins instance to scan for credentials offline.
Evidence of this may be found in the Jenkins docker logs.
Anonymous users attempting to access a resource that they don't have permission to view is logged by default in Jenkins and may be used to find console output scraping. Look for patterns of mass scanning by anonymous users to prove this.
Documentation of this technique and various others can be found in the links below.
To ensure that there is no additional exposure of credentials in the log files, trufflehog should be run against the Jenkins_home directory or the Jenkins_home/jobs directory.
If there are any exposed credentials found, they should be rotated immediately and the logs for the application they provide access to should be investigated to ensure there is no unauthorized access.
Default Logs:
Active Directory Plugin:
Failed authentications to valid Active Directory users
Anonymous users:
Whenever an anonymous user browses to a location they don't have access to, the attempt and URL is logged by default.
Not Default:
Script Console output and commands not logged by default.
Successful user authentications and failed user authentications are not logged by default.
Job creation, changes, and executions are not logged in Jenkins Docker logs.
Access logs are NOT enabled by default, you need to enable it by creating a log recorder that is monitoring the following logger:
jenkins.security.SecurityListener
The log recorder file will contain what logger target is being monitored and is located in the following path:
/var/jenkins_home/logs/<log name>.xml
Jenkins is accessible from the internet without restrictions.
Credentials are exposed in workspaces or console output.
MFA is not enabled.
Weak username/passwords for users allowed to access Jenkins.
Jenkins is not patched and can be exploited.
Users are overprivileged and allowed to execute commands from the Script Console.
Least Privilege:
Jenkins service account should not have root access. Practice least privilege to avoid Groovy scripts from reading credentials.xml file.
Practice least privilege in Jenkins accounts, avoid "Logged in users can do anything" setting.
Any user with job creation and configuration privileges has shell access to the nodes because job configuration allows an arbitrary command to run on the nodes.
Do not allow anonymous access.
Logging:
By default, Jenkins does not enable access logging, this must be turned on.
Use logging plugins like "Audit Log" and "Audit Trail" to track job execution, script console execution, or login events.
CVEs:
Ensure Jenkins and its plugins are updated to avoid exploitation of CVEs.
Access Control:
Ensure Jenkins is not exposed to the internet and if it is, only allowlist specific IPs that should have access to it.