| name | sc-lang-java |
| description | Java/Kotlin-specific security deep scan |
| license | MIT |
| metadata | {"author":"ersinkoc","category":"security","version":"1.0.0"} |
SC: Java/Kotlin Security Deep Scan
Purpose
Detects Java/Kotlin-specific security anti-patterns including deserialization gadget chains, JNDI injection (Log4Shell patterns), Spring framework vulnerabilities, XML parsing XXE, and Kotlin-specific interop risks. Covers the JVM ecosystem's unique attack surface.
Activation
Activates when Java or Kotlin is detected in security-report/architecture.md.
Checklist Reference
References references/java-security-checklist.md.
Java/Kotlin-Specific Vulnerability Patterns
Category 1: Java Deserialization
ObjectInputStream ois = new ObjectInputStream(socketInputStream);
Object obj = ois.readObject();
ObjectInputFilter filter = ObjectInputFilter.Config.createFilter(
"com.myapp.dto.*;!*"
);
ois.setObjectInputFilter(filter);
Category 2: JNDI Injection (Log4Shell Pattern)
ctx.lookup(userInput);
System.setProperty("log4j2.formatMsgNoLookups", "true");
Category 3: Spring SpEL Injection
SpelExpressionParser parser = new SpelExpressionParser();
Expression exp = parser.parseExpression(userInput);
Object result = exp.getValue();
EvaluationContext context = SimpleEvaluationContext.forReadOnlyDataBinding().build();
Object result = exp.getValue(context);
Category 4: Spring Actuator Exposure
management:
endpoints:
web:
exposure:
include: "*"
management:
endpoints:
web:
exposure:
include: health,info
Category 5: Hibernate HQL Injection
String hql = "FROM User WHERE name = '" + name + "'";
Query query = session.createQuery(hql);
Query query = session.createQuery("FROM User WHERE name = :name");
query.setParameter("name", name);
Category 6: Servlet Parameter Pollution
String role = request.getParameter("role");
String[] roles = request.getParameterValues("role");
Category 7: Runtime.exec Command Injection
Runtime.getRuntime().exec("cmd /c dir " + userInput);
new ProcessBuilder("dir", userInput).start();
Category 8: XML Parsing XXE
DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
Document doc = dbf.newDocumentBuilder().parse(inputStream);
dbf.setFeature("http://apache.org/xml/features/disallow-doctype-decl", true);
dbf.setFeature("http://xml.org/sax/features/external-general-entities", false);
dbf.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
Category 9: Kotlin Null Safety via Java Interop
val name: String = javaObject.getName()
val name: String? = javaObject.getName()
val safeName = name ?: "default"
Category 10: Kotlin Coroutine Exception Handling
scope.launch {
riskyOperation()
}
val handler = CoroutineExceptionHandler { _, ex -> log.error("Error", ex) }
scope.launch(handler + SupervisorJob()) {
riskyOperation()
}
Category 11: Reflection Security
Field field = User.class.getDeclaredField(userInput);
field.setAccessible(true);
field.set(user, newValue);
Category 12: JDBC Connection String Injection
String url = "jdbc:mysql://db:3306/" + userInput;
DriverManager.getConnection(url);
Category 13: SecureRandom vs Random
Random random = new Random();
String token = Long.toHexString(random.nextLong());
SecureRandom random = new SecureRandom();
byte[] bytes = new byte[32];
random.nextBytes(bytes);
Category 14: Gradle/Maven Supply Chain
- Check for untrusted plugin repositories in build.gradle
- Review custom Gradle plugins for code execution
- Verify dependency checksums
- Check for repository substitution attacks (internal→public)
Category 15: Thymeleaf SSTI
String template = "Hello " + userInput;
templateEngine.process(template, context);
model.addAttribute("name", userInput);
templateEngine.process("hello", context);
Category 16: JSP Expression Language Injection
<!-- VULNERABLE: User input in EL expression -->
<c:out value="${param.name}" /> <!-- Generally safe with c:out -->
${param.name} <!-- Direct EL is NOT auto-escaped in JSP! XSS -->
<!-- SAFE: Use JSTL c:out or fn:escapeXml -->
<c:out value="${param.name}" escapeXml="true" />
Category 17: Spring Mass Assignment
@PostMapping("/users")
public User create(@ModelAttribute User user) {
return repo.save(user);
}
public User create(@RequestBody CreateUserDTO dto) { }
@InitBinder
public void initBinder(WebDataBinder binder) {
binder.setDisallowedFields("role", "isAdmin");
}
Category 18: Spring Security Misconfiguration
http.csrf().disable()
.authorizeRequests().anyRequest().permitAll();
http.csrf().csrfTokenRepository(CookieCsrfTokenRepository.withHttpOnlyFalse())
.authorizeRequests()
.antMatchers("/api/public/**").permitAll()
.antMatchers("/api/admin/**").hasRole("ADMIN")
.anyRequest().authenticated();
Category 19: File Upload Security
@PostMapping("/upload")
public void upload(@RequestParam("file") MultipartFile file) {
file.transferTo(new File("/uploads/" + file.getOriginalFilename()));
}
if (!ALLOWED_TYPES.contains(file.getContentType())) throw new BadRequest();
String filename = UUID.randomUUID() + getExtension(file.getOriginalFilename());
Category 20: Jackson Polymorphic Deserialization
ObjectMapper mapper = new ObjectMapper();
mapper.enableDefaultTyping();
mapper.activateDefaultTyping(
mapper.getPolymorphicTypeValidator(),
ObjectMapper.DefaultTyping.NON_FINAL
);
Output Format
Finding: JAVA-{NNN}
- Title: Java/Kotlin-specific vulnerability
- Severity: Critical | High | Medium | Low
- Confidence: 0-100
- File: file/path:line
- Vulnerability Type: CWE-XXX
- Description: What was found
- Remediation: Java-idiomatic fix
- References: CWE link, Spring/JVM documentation