Merge pull request from GHSA-r2hc-pmr7-4c9r
* Configured XML parsers to resist XXE attacks Signed-off-by: Kai Kreuzer <kai@openhab.org> * added fix for avmfritz Signed-off-by: Kai Kreuzer <kai@openhab.org> * added fix for sonos Signed-off-by: Kai Kreuzer <kai@openhab.org> * added fix for vitotronic and bosesoundtouch Signed-off-by: Kai Kreuzer <kai@openhab.org> * changed avmfritz to singleton pattern Signed-off-by: Kai Kreuzer <kai@openhab.org> * addressed roku binding Signed-off-by: Kai Kreuzer <kai@openhab.org> * address all uses of DocumentBuilderFactory Signed-off-by: Kai Kreuzer <kai@openhab.org> * fixed other occurrences in roku binding Signed-off-by: Kai Kreuzer <kai@openhab.org>
This commit is contained in:
parent
5682292c0b
commit
b0a15b48a3
|
@ -18,6 +18,8 @@ import java.io.StringReader;
|
||||||
|
|
||||||
import javax.xml.bind.JAXBException;
|
import javax.xml.bind.JAXBException;
|
||||||
import javax.xml.bind.Unmarshaller;
|
import javax.xml.bind.Unmarshaller;
|
||||||
|
import javax.xml.stream.XMLStreamException;
|
||||||
|
import javax.xml.stream.XMLStreamReader;
|
||||||
|
|
||||||
import org.eclipse.jdt.annotation.NonNullByDefault;
|
import org.eclipse.jdt.annotation.NonNullByDefault;
|
||||||
import org.openhab.binding.avmfritz.internal.dto.DeviceListModel;
|
import org.openhab.binding.avmfritz.internal.dto.DeviceListModel;
|
||||||
|
@ -62,15 +64,16 @@ public class FritzAhaUpdateCallback extends FritzAhaReauthCallback {
|
||||||
logger.trace("Received State response {}", response);
|
logger.trace("Received State response {}", response);
|
||||||
if (isValidRequest()) {
|
if (isValidRequest()) {
|
||||||
try {
|
try {
|
||||||
|
XMLStreamReader xsr = JAXBUtils.XMLINPUTFACTORY.createXMLStreamReader(new StringReader(response));
|
||||||
Unmarshaller unmarshaller = JAXBUtils.JAXBCONTEXT_DEVICES.createUnmarshaller();
|
Unmarshaller unmarshaller = JAXBUtils.JAXBCONTEXT_DEVICES.createUnmarshaller();
|
||||||
DeviceListModel model = (DeviceListModel) unmarshaller.unmarshal(new StringReader(response));
|
DeviceListModel model = (DeviceListModel) unmarshaller.unmarshal(xsr);
|
||||||
if (model != null) {
|
if (model != null) {
|
||||||
handler.onDeviceListAdded(model.getDevicelist());
|
handler.onDeviceListAdded(model.getDevicelist());
|
||||||
} else {
|
} else {
|
||||||
logger.debug("no model in response");
|
logger.debug("no model in response");
|
||||||
}
|
}
|
||||||
handler.setStatusInfo(ThingStatus.ONLINE, ThingStatusDetail.NONE, null);
|
handler.setStatusInfo(ThingStatus.ONLINE, ThingStatusDetail.NONE, null);
|
||||||
} catch (JAXBException e) {
|
} catch (JAXBException | XMLStreamException e) {
|
||||||
logger.error("Exception creating Unmarshaller: {}", e.getLocalizedMessage(), e);
|
logger.error("Exception creating Unmarshaller: {}", e.getLocalizedMessage(), e);
|
||||||
handler.setStatusInfo(ThingStatus.OFFLINE, ThingStatusDetail.COMMUNICATION_ERROR,
|
handler.setStatusInfo(ThingStatus.OFFLINE, ThingStatusDetail.COMMUNICATION_ERROR,
|
||||||
e.getLocalizedMessage());
|
e.getLocalizedMessage());
|
||||||
|
|
|
@ -18,6 +18,8 @@ import java.io.StringReader;
|
||||||
|
|
||||||
import javax.xml.bind.JAXBException;
|
import javax.xml.bind.JAXBException;
|
||||||
import javax.xml.bind.Unmarshaller;
|
import javax.xml.bind.Unmarshaller;
|
||||||
|
import javax.xml.stream.XMLStreamException;
|
||||||
|
import javax.xml.stream.XMLStreamReader;
|
||||||
|
|
||||||
import org.eclipse.jdt.annotation.NonNullByDefault;
|
import org.eclipse.jdt.annotation.NonNullByDefault;
|
||||||
import org.openhab.binding.avmfritz.internal.dto.templates.TemplateListModel;
|
import org.openhab.binding.avmfritz.internal.dto.templates.TemplateListModel;
|
||||||
|
@ -58,14 +60,15 @@ public class FritzAhaUpdateTemplatesCallback extends FritzAhaReauthCallback {
|
||||||
logger.trace("Received response '{}'", response);
|
logger.trace("Received response '{}'", response);
|
||||||
if (isValidRequest()) {
|
if (isValidRequest()) {
|
||||||
try {
|
try {
|
||||||
|
XMLStreamReader xsr = JAXBUtils.XMLINPUTFACTORY.createXMLStreamReader(new StringReader(response));
|
||||||
Unmarshaller unmarshaller = JAXBUtils.JAXBCONTEXT_TEMPLATES.createUnmarshaller();
|
Unmarshaller unmarshaller = JAXBUtils.JAXBCONTEXT_TEMPLATES.createUnmarshaller();
|
||||||
TemplateListModel model = (TemplateListModel) unmarshaller.unmarshal(new StringReader(response));
|
TemplateListModel model = (TemplateListModel) unmarshaller.unmarshal(xsr);
|
||||||
if (model != null) {
|
if (model != null) {
|
||||||
handler.addTemplateList(model.getTemplates());
|
handler.addTemplateList(model.getTemplates());
|
||||||
} else {
|
} else {
|
||||||
logger.debug("no template in response");
|
logger.debug("no template in response");
|
||||||
}
|
}
|
||||||
} catch (JAXBException e) {
|
} catch (JAXBException | XMLStreamException e) {
|
||||||
logger.error("Exception creating Unmarshaller: {}", e.getLocalizedMessage(), e);
|
logger.error("Exception creating Unmarshaller: {}", e.getLocalizedMessage(), e);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
|
|
@ -14,6 +14,7 @@ package org.openhab.binding.avmfritz.internal.util;
|
||||||
|
|
||||||
import javax.xml.bind.JAXBContext;
|
import javax.xml.bind.JAXBContext;
|
||||||
import javax.xml.bind.JAXBException;
|
import javax.xml.bind.JAXBException;
|
||||||
|
import javax.xml.stream.XMLInputFactory;
|
||||||
|
|
||||||
import org.eclipse.jdt.annotation.NonNullByDefault;
|
import org.eclipse.jdt.annotation.NonNullByDefault;
|
||||||
import org.eclipse.jdt.annotation.Nullable;
|
import org.eclipse.jdt.annotation.Nullable;
|
||||||
|
@ -34,6 +35,7 @@ public class JAXBUtils {
|
||||||
|
|
||||||
public static final @Nullable JAXBContext JAXBCONTEXT_DEVICES = initJAXBContextDevices();
|
public static final @Nullable JAXBContext JAXBCONTEXT_DEVICES = initJAXBContextDevices();
|
||||||
public static final @Nullable JAXBContext JAXBCONTEXT_TEMPLATES = initJAXBContextTemplates();
|
public static final @Nullable JAXBContext JAXBCONTEXT_TEMPLATES = initJAXBContextTemplates();
|
||||||
|
public static final XMLInputFactory XMLINPUTFACTORY = initXMLInputFactory();
|
||||||
|
|
||||||
private static @Nullable JAXBContext initJAXBContextDevices() {
|
private static @Nullable JAXBContext initJAXBContextDevices() {
|
||||||
try {
|
try {
|
||||||
|
@ -52,4 +54,11 @@ public class JAXBUtils {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static XMLInputFactory initXMLInputFactory() {
|
||||||
|
XMLInputFactory xif = XMLInputFactory.newInstance();
|
||||||
|
xif.setProperty(XMLInputFactory.IS_SUPPORTING_EXTERNAL_ENTITIES, false);
|
||||||
|
xif.setProperty(XMLInputFactory.SUPPORT_DTD, false);
|
||||||
|
return xif;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -41,6 +41,7 @@ public class XMLResponseProcessor {
|
||||||
|
|
||||||
public void handleMessage(String msg) throws SAXException, IOException {
|
public void handleMessage(String msg) throws SAXException, IOException {
|
||||||
XMLReader reader = XMLReaderFactory.createXMLReader();
|
XMLReader reader = XMLReaderFactory.createXMLReader();
|
||||||
|
reader.setFeature("http://apache.org/xml/features/disallow-doctype-decl", true);
|
||||||
reader.setContentHandler(new XMLResponseHandler(handler, stateSwitchingMap));
|
reader.setContentHandler(new XMLResponseHandler(handler, stateSwitchingMap));
|
||||||
reader.parse(new InputSource(new StringReader(msg)));
|
reader.parse(new InputSource(new StringReader(msg)));
|
||||||
}
|
}
|
||||||
|
|
|
@ -309,6 +309,8 @@ public class DenonMarantzHttpConnector extends DenonMarantzConnector {
|
||||||
if (StringUtils.isNotBlank(result)) {
|
if (StringUtils.isNotBlank(result)) {
|
||||||
JAXBContext jc = JAXBContext.newInstance(response);
|
JAXBContext jc = JAXBContext.newInstance(response);
|
||||||
XMLInputFactory xif = XMLInputFactory.newInstance();
|
XMLInputFactory xif = XMLInputFactory.newInstance();
|
||||||
|
xif.setProperty(XMLInputFactory.IS_SUPPORTING_EXTERNAL_ENTITIES, false);
|
||||||
|
xif.setProperty(XMLInputFactory.SUPPORT_DTD, false);
|
||||||
XMLStreamReader xsr = xif.createXMLStreamReader(IOUtils.toInputStream(result));
|
XMLStreamReader xsr = xif.createXMLStreamReader(IOUtils.toInputStream(result));
|
||||||
xsr = new PropertyRenamerDelegate(xsr);
|
xsr = new PropertyRenamerDelegate(xsr);
|
||||||
|
|
||||||
|
|
|
@ -261,8 +261,15 @@ public class DenonMarantzHandler extends BaseThingHandler implements DenonMarant
|
||||||
|
|
||||||
if (status == HttpURLConnection.HTTP_OK && response != null) {
|
if (status == HttpURLConnection.HTTP_OK && response != null) {
|
||||||
DocumentBuilderFactory domFactory = DocumentBuilderFactory.newInstance();
|
DocumentBuilderFactory domFactory = DocumentBuilderFactory.newInstance();
|
||||||
DocumentBuilder builder;
|
|
||||||
try {
|
try {
|
||||||
|
// see
|
||||||
|
// https://cheatsheetseries.owasp.org/cheatsheets/XML_External_Entity_Prevention_Cheat_Sheet.html
|
||||||
|
domFactory.setFeature("http://xml.org/sax/features/external-general-entities", false);
|
||||||
|
domFactory.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
|
||||||
|
domFactory.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false);
|
||||||
|
domFactory.setXIncludeAware(false);
|
||||||
|
domFactory.setExpandEntityReferences(false);
|
||||||
|
DocumentBuilder builder;
|
||||||
builder = domFactory.newDocumentBuilder();
|
builder = domFactory.newDocumentBuilder();
|
||||||
Document dDoc = builder.parse(new InputSource(new StringReader(response.getContentAsString())));
|
Document dDoc = builder.parse(new InputSource(new StringReader(response.getContentAsString())));
|
||||||
XPath xPath = XPathFactory.newInstance().newXPath();
|
XPath xPath = XPathFactory.newInstance().newXPath();
|
||||||
|
|
|
@ -155,7 +155,14 @@ public abstract class DLinkHNAPCommunication {
|
||||||
uri = new URI("http://" + ipAddress + "/HNAP1");
|
uri = new URI("http://" + ipAddress + "/HNAP1");
|
||||||
httpClient.start();
|
httpClient.start();
|
||||||
|
|
||||||
parser = DocumentBuilderFactory.newInstance().newDocumentBuilder();
|
DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
|
||||||
|
// see https://cheatsheetseries.owasp.org/cheatsheets/XML_External_Entity_Prevention_Cheat_Sheet.html
|
||||||
|
dbf.setFeature("http://xml.org/sax/features/external-general-entities", false);
|
||||||
|
dbf.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
|
||||||
|
dbf.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false);
|
||||||
|
dbf.setXIncludeAware(false);
|
||||||
|
dbf.setExpandEntityReferences(false);
|
||||||
|
parser = dbf.newDocumentBuilder();
|
||||||
|
|
||||||
final MessageFactory messageFactory = MessageFactory.newInstance();
|
final MessageFactory messageFactory = MessageFactory.newInstance();
|
||||||
requestAction = messageFactory.createMessage();
|
requestAction = messageFactory.createMessage();
|
||||||
|
|
|
@ -81,9 +81,16 @@ public class Enigma2Client {
|
||||||
private final Enigma2HttpClient enigma2HttpClient;
|
private final Enigma2HttpClient enigma2HttpClient;
|
||||||
private final DocumentBuilderFactory factory;
|
private final DocumentBuilderFactory factory;
|
||||||
|
|
||||||
public Enigma2Client(String host, @Nullable String user, @Nullable String password, int requestTimeout) {
|
public Enigma2Client(String host, @Nullable String user, @Nullable String password, int requestTimeout)
|
||||||
this.enigma2HttpClient = new Enigma2HttpClient(requestTimeout);
|
throws ParserConfigurationException {
|
||||||
this.factory = DocumentBuilderFactory.newInstance();
|
enigma2HttpClient = new Enigma2HttpClient(requestTimeout);
|
||||||
|
factory = DocumentBuilderFactory.newInstance();
|
||||||
|
// see https://cheatsheetseries.owasp.org/cheatsheets/XML_External_Entity_Prevention_Cheat_Sheet.html
|
||||||
|
factory.setFeature("http://xml.org/sax/features/external-general-entities", false);
|
||||||
|
factory.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
|
||||||
|
factory.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false);
|
||||||
|
factory.setXIncludeAware(false);
|
||||||
|
factory.setExpandEntityReferences(false);
|
||||||
if (StringUtils.isNotEmpty(user) && StringUtils.isNotEmpty(password)) {
|
if (StringUtils.isNotEmpty(user) && StringUtils.isNotEmpty(password)) {
|
||||||
this.host = "http://" + user + ":" + password + "@" + host;
|
this.host = "http://" + user + ":" + password + "@" + host;
|
||||||
} else {
|
} else {
|
||||||
|
|
|
@ -105,6 +105,12 @@ public class Client {
|
||||||
public Client() {
|
public Client() {
|
||||||
documentBuilderFactory.setNamespaceAware(true);
|
documentBuilderFactory.setNamespaceAware(true);
|
||||||
try {
|
try {
|
||||||
|
// see https://cheatsheetseries.owasp.org/cheatsheets/XML_External_Entity_Prevention_Cheat_Sheet.html
|
||||||
|
documentBuilderFactory.setFeature("http://xml.org/sax/features/external-general-entities", false);
|
||||||
|
documentBuilderFactory.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
|
||||||
|
documentBuilderFactory.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false);
|
||||||
|
documentBuilderFactory.setXIncludeAware(false);
|
||||||
|
documentBuilderFactory.setExpandEntityReferences(false);
|
||||||
documentBuilder = documentBuilderFactory.newDocumentBuilder();
|
documentBuilder = documentBuilderFactory.newDocumentBuilder();
|
||||||
} catch (ParserConfigurationException e) {
|
} catch (ParserConfigurationException e) {
|
||||||
throw new IllegalStateException(e);
|
throw new IllegalStateException(e);
|
||||||
|
|
|
@ -209,6 +209,12 @@ public class FrontierSiliconRadioApiResult {
|
||||||
private Document getXmlDocFromString(String xmlString)
|
private Document getXmlDocFromString(String xmlString)
|
||||||
throws ParserConfigurationException, SAXException, IOException {
|
throws ParserConfigurationException, SAXException, IOException {
|
||||||
final DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
|
final DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
|
||||||
|
// see https://cheatsheetseries.owasp.org/cheatsheets/XML_External_Entity_Prevention_Cheat_Sheet.html
|
||||||
|
factory.setFeature("http://xml.org/sax/features/external-general-entities", false);
|
||||||
|
factory.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
|
||||||
|
factory.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false);
|
||||||
|
factory.setXIncludeAware(false);
|
||||||
|
factory.setExpandEntityReferences(false);
|
||||||
final DocumentBuilder builder = factory.newDocumentBuilder();
|
final DocumentBuilder builder = factory.newDocumentBuilder();
|
||||||
final Document xmlDocument = builder.parse(new InputSource(new StringReader(xmlString)));
|
final Document xmlDocument = builder.parse(new InputSource(new StringReader(xmlString)));
|
||||||
return xmlDocument;
|
return xmlDocument;
|
||||||
|
|
|
@ -61,7 +61,14 @@ public class StatusFileInterpreter {
|
||||||
|
|
||||||
public void read() {
|
public void read() {
|
||||||
try {
|
try {
|
||||||
DocumentBuilder builder = DocumentBuilderFactory.newInstance().newDocumentBuilder();
|
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
|
||||||
|
// see https://cheatsheetseries.owasp.org/cheatsheets/XML_External_Entity_Prevention_Cheat_Sheet.html
|
||||||
|
factory.setFeature("http://xml.org/sax/features/external-general-entities", false);
|
||||||
|
factory.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
|
||||||
|
factory.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false);
|
||||||
|
factory.setXIncludeAware(false);
|
||||||
|
factory.setExpandEntityReferences(false);
|
||||||
|
DocumentBuilder builder = factory.newDocumentBuilder();
|
||||||
String statusPage = HttpUtil.executeUrl("GET", String.format(URL_TEMPLATE, hostname), 5000);
|
String statusPage = HttpUtil.executeUrl("GET", String.format(URL_TEMPLATE, hostname), 5000);
|
||||||
InputStream inputStream = new ByteArrayInputStream(statusPage.getBytes());
|
InputStream inputStream = new ByteArrayInputStream(statusPage.getBytes());
|
||||||
Document document = builder.parse(inputStream);
|
Document document = builder.parse(inputStream);
|
||||||
|
|
|
@ -47,6 +47,9 @@ public class XmlRpcResponse implements RpcResponse {
|
||||||
throws SAXException, ParserConfigurationException, IOException {
|
throws SAXException, ParserConfigurationException, IOException {
|
||||||
SAXParserFactory factory = SAXParserFactory.newInstance();
|
SAXParserFactory factory = SAXParserFactory.newInstance();
|
||||||
SAXParser saxParser = factory.newSAXParser();
|
SAXParser saxParser = factory.newSAXParser();
|
||||||
|
factory.setFeature("https://xml.org/sax/features/external-general-entities", false);
|
||||||
|
saxParser.getXMLReader().setFeature("https://xml.org/sax/features/external-general-entities", false);
|
||||||
|
factory.setFeature("https://apache.org/xml/features/disallow-doctype-decl", true);
|
||||||
InputSource inputSource = new InputSource(is);
|
InputSource inputSource = new InputSource(is);
|
||||||
inputSource.setEncoding(encoding);
|
inputSource.setEncoding(encoding);
|
||||||
saxParser.parse(inputSource, new XmlRpcHandler());
|
saxParser.parse(inputSource, new XmlRpcHandler());
|
||||||
|
|
|
@ -50,7 +50,7 @@ public class HPWebServerClient {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Creates a new HP Web Server Client object.
|
* Creates a new HP Web Server Client object.
|
||||||
*
|
*
|
||||||
* @param httpClient {HttpClient} The HttpClient to use for HTTP requests.
|
* @param httpClient {HttpClient} The HttpClient to use for HTTP requests.
|
||||||
* @param address The address for the Embedded Web Server.
|
* @param address The address for the Embedded Web Server.
|
||||||
*/
|
*/
|
||||||
|
@ -63,7 +63,7 @@ public class HPWebServerClient {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets the Status information from the Embedded Web Server.
|
* Gets the Status information from the Embedded Web Server.
|
||||||
*
|
*
|
||||||
* @return The status information.
|
* @return The status information.
|
||||||
*/
|
*/
|
||||||
public HPServerResult<HPStatus> getStatus() {
|
public HPServerResult<HPStatus> getStatus() {
|
||||||
|
@ -84,7 +84,7 @@ public class HPWebServerClient {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets the Usage information from the Embedded Web Server.
|
* Gets the Usage information from the Embedded Web Server.
|
||||||
*
|
*
|
||||||
* @return The usage information.
|
* @return The usage information.
|
||||||
*/
|
*/
|
||||||
public HPServerResult<HPUsage> getUsage() {
|
public HPServerResult<HPUsage> getUsage() {
|
||||||
|
@ -120,6 +120,12 @@ public class HPWebServerClient {
|
||||||
|
|
||||||
private synchronized Document getDocument(String contentAsString)
|
private synchronized Document getDocument(String contentAsString)
|
||||||
throws ParserConfigurationException, SAXException, IOException {
|
throws ParserConfigurationException, SAXException, IOException {
|
||||||
|
// see https://cheatsheetseries.owasp.org/cheatsheets/XML_External_Entity_Prevention_Cheat_Sheet.html
|
||||||
|
factory.setFeature("http://xml.org/sax/features/external-general-entities", false);
|
||||||
|
factory.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
|
||||||
|
factory.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false);
|
||||||
|
factory.setXIncludeAware(false);
|
||||||
|
factory.setExpandEntityReferences(false);
|
||||||
DocumentBuilder builder = factory.newDocumentBuilder();
|
DocumentBuilder builder = factory.newDocumentBuilder();
|
||||||
InputSource source = new InputSource(new StringReader(contentAsString));
|
InputSource source = new InputSource(new StringReader(contentAsString));
|
||||||
return builder.parse(source);
|
return builder.parse(source);
|
||||||
|
|
|
@ -53,6 +53,12 @@ public class ProjectFileUtils {
|
||||||
File fXmlFile = new File(filePath);
|
File fXmlFile = new File(filePath);
|
||||||
DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
|
DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
|
||||||
try {
|
try {
|
||||||
|
// see https://cheatsheetseries.owasp.org/cheatsheets/XML_External_Entity_Prevention_Cheat_Sheet.html
|
||||||
|
dbFactory.setFeature("http://xml.org/sax/features/external-general-entities", false);
|
||||||
|
dbFactory.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
|
||||||
|
dbFactory.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false);
|
||||||
|
dbFactory.setXIncludeAware(false);
|
||||||
|
dbFactory.setExpandEntityReferences(false);
|
||||||
DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
|
DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
|
||||||
Document doc = dBuilder.parse(fXmlFile);
|
Document doc = dBuilder.parse(fXmlFile);
|
||||||
return doc;
|
return doc;
|
||||||
|
|
|
@ -78,6 +78,12 @@ public class DeviceTypeLoader {
|
||||||
*/
|
*/
|
||||||
public void loadDeviceTypesXML(InputStream in) throws ParserConfigurationException, SAXException, IOException {
|
public void loadDeviceTypesXML(InputStream in) throws ParserConfigurationException, SAXException, IOException {
|
||||||
DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
|
DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
|
||||||
|
// see https://cheatsheetseries.owasp.org/cheatsheets/XML_External_Entity_Prevention_Cheat_Sheet.html
|
||||||
|
dbFactory.setFeature("http://xml.org/sax/features/external-general-entities", false);
|
||||||
|
dbFactory.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
|
||||||
|
dbFactory.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false);
|
||||||
|
dbFactory.setXIncludeAware(false);
|
||||||
|
dbFactory.setExpandEntityReferences(false);
|
||||||
DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
|
DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
|
||||||
Document doc = dBuilder.parse(in);
|
Document doc = dBuilder.parse(in);
|
||||||
doc.getDocumentElement().normalize();
|
doc.getDocumentElement().normalize();
|
||||||
|
|
|
@ -51,6 +51,12 @@ public class FeatureTemplateLoader {
|
||||||
List<FeatureTemplate> features = new ArrayList<>();
|
List<FeatureTemplate> features = new ArrayList<>();
|
||||||
try {
|
try {
|
||||||
DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
|
DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
|
||||||
|
// see https://cheatsheetseries.owasp.org/cheatsheets/XML_External_Entity_Prevention_Cheat_Sheet.html
|
||||||
|
dbFactory.setFeature("http://xml.org/sax/features/external-general-entities", false);
|
||||||
|
dbFactory.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
|
||||||
|
dbFactory.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false);
|
||||||
|
dbFactory.setXIncludeAware(false);
|
||||||
|
dbFactory.setExpandEntityReferences(false);
|
||||||
DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
|
DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
|
||||||
// Parse it!
|
// Parse it!
|
||||||
Document doc = dBuilder.parse(input);
|
Document doc = dBuilder.parse(input);
|
||||||
|
|
|
@ -55,6 +55,12 @@ public class XMLMessageReader {
|
||||||
Map<String, Msg> messageMap = new HashMap<>();
|
Map<String, Msg> messageMap = new HashMap<>();
|
||||||
try {
|
try {
|
||||||
DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
|
DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
|
||||||
|
// see https://cheatsheetseries.owasp.org/cheatsheets/XML_External_Entity_Prevention_Cheat_Sheet.html
|
||||||
|
dbFactory.setFeature("http://xml.org/sax/features/external-general-entities", false);
|
||||||
|
dbFactory.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
|
||||||
|
dbFactory.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false);
|
||||||
|
dbFactory.setXIncludeAware(false);
|
||||||
|
dbFactory.setExpandEntityReferences(false);
|
||||||
DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
|
DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
|
||||||
// Parse it!
|
// Parse it!
|
||||||
Document doc = dBuilder.parse(input);
|
Document doc = dBuilder.parse(input);
|
||||||
|
|
|
@ -498,6 +498,12 @@ public class OnkyoHandler extends UpnpAudioSinkHandler implements OnkyoEventList
|
||||||
private void processInfo(String infoXML) {
|
private void processInfo(String infoXML) {
|
||||||
try {
|
try {
|
||||||
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
|
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
|
||||||
|
// see https://cheatsheetseries.owasp.org/cheatsheets/XML_External_Entity_Prevention_Cheat_Sheet.html
|
||||||
|
factory.setFeature("http://xml.org/sax/features/external-general-entities", false);
|
||||||
|
factory.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
|
||||||
|
factory.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false);
|
||||||
|
factory.setXIncludeAware(false);
|
||||||
|
factory.setExpandEntityReferences(false);
|
||||||
DocumentBuilder builder = factory.newDocumentBuilder();
|
DocumentBuilder builder = factory.newDocumentBuilder();
|
||||||
try (StringReader sr = new StringReader(infoXML)) {
|
try (StringReader sr = new StringReader(infoXML)) {
|
||||||
InputSource is = new InputSource(sr);
|
InputSource is = new InputSource(sr);
|
||||||
|
|
|
@ -14,6 +14,7 @@ package org.openhab.binding.roku.internal.communication;
|
||||||
|
|
||||||
import javax.xml.bind.JAXBContext;
|
import javax.xml.bind.JAXBContext;
|
||||||
import javax.xml.bind.JAXBException;
|
import javax.xml.bind.JAXBException;
|
||||||
|
import javax.xml.stream.XMLInputFactory;
|
||||||
|
|
||||||
import org.eclipse.jdt.annotation.NonNullByDefault;
|
import org.eclipse.jdt.annotation.NonNullByDefault;
|
||||||
import org.eclipse.jdt.annotation.Nullable;
|
import org.eclipse.jdt.annotation.Nullable;
|
||||||
|
@ -38,6 +39,7 @@ public class JAXBUtils {
|
||||||
public static final @Nullable JAXBContext JAXBCONTEXT_APPS = initJAXBContextApps();
|
public static final @Nullable JAXBContext JAXBCONTEXT_APPS = initJAXBContextApps();
|
||||||
public static final @Nullable JAXBContext JAXBCONTEXT_DEVICE_INFO = initJAXBContextDeviceInfo();
|
public static final @Nullable JAXBContext JAXBCONTEXT_DEVICE_INFO = initJAXBContextDeviceInfo();
|
||||||
public static final @Nullable JAXBContext JAXBCONTEXT_PLAYER = initJAXBContextPlayer();
|
public static final @Nullable JAXBContext JAXBCONTEXT_PLAYER = initJAXBContextPlayer();
|
||||||
|
public static final XMLInputFactory XMLINPUTFACTORY = initXMLInputFactory();
|
||||||
|
|
||||||
private static @Nullable JAXBContext initJAXBContextActiveApp() {
|
private static @Nullable JAXBContext initJAXBContextActiveApp() {
|
||||||
try {
|
try {
|
||||||
|
@ -74,4 +76,11 @@ public class JAXBUtils {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static XMLInputFactory initXMLInputFactory() {
|
||||||
|
XMLInputFactory xif = XMLInputFactory.newInstance();
|
||||||
|
xif.setProperty(XMLInputFactory.IS_SUPPORTING_EXTERNAL_ENTITIES, false);
|
||||||
|
xif.setProperty(XMLInputFactory.SUPPORT_DTD, false);
|
||||||
|
return xif;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -20,6 +20,8 @@ import java.util.concurrent.TimeoutException;
|
||||||
import javax.xml.bind.JAXBContext;
|
import javax.xml.bind.JAXBContext;
|
||||||
import javax.xml.bind.JAXBException;
|
import javax.xml.bind.JAXBException;
|
||||||
import javax.xml.bind.Unmarshaller;
|
import javax.xml.bind.Unmarshaller;
|
||||||
|
import javax.xml.stream.XMLStreamException;
|
||||||
|
import javax.xml.stream.XMLStreamReader;
|
||||||
|
|
||||||
import org.eclipse.jdt.annotation.NonNullByDefault;
|
import org.eclipse.jdt.annotation.NonNullByDefault;
|
||||||
import org.eclipse.jetty.client.HttpClient;
|
import org.eclipse.jetty.client.HttpClient;
|
||||||
|
@ -94,14 +96,16 @@ public class RokuCommunicator {
|
||||||
if (ctx != null) {
|
if (ctx != null) {
|
||||||
Unmarshaller unmarshaller = ctx.createUnmarshaller();
|
Unmarshaller unmarshaller = ctx.createUnmarshaller();
|
||||||
if (unmarshaller != null) {
|
if (unmarshaller != null) {
|
||||||
DeviceInfo device = (DeviceInfo) unmarshaller.unmarshal(new StringReader(getCommand(urlQryDevice)));
|
XMLStreamReader xsr = JAXBUtils.XMLINPUTFACTORY
|
||||||
|
.createXMLStreamReader(new StringReader(getCommand(urlQryDevice)));
|
||||||
|
DeviceInfo device = (DeviceInfo) unmarshaller.unmarshal(xsr);
|
||||||
if (device != null) {
|
if (device != null) {
|
||||||
return device;
|
return device;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
throw new RokuHttpException("No DeviceInfo model in response");
|
throw new RokuHttpException("No DeviceInfo model in response");
|
||||||
} catch (JAXBException e) {
|
} catch (JAXBException | XMLStreamException e) {
|
||||||
throw new RokuHttpException("Exception creating DeviceInfo Unmarshaller: " + e.getLocalizedMessage());
|
throw new RokuHttpException("Exception creating DeviceInfo Unmarshaller: " + e.getLocalizedMessage());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -118,8 +122,10 @@ public class RokuCommunicator {
|
||||||
if (ctx != null) {
|
if (ctx != null) {
|
||||||
Unmarshaller unmarshaller = ctx.createUnmarshaller();
|
Unmarshaller unmarshaller = ctx.createUnmarshaller();
|
||||||
if (unmarshaller != null) {
|
if (unmarshaller != null) {
|
||||||
|
XMLStreamReader xsr = JAXBUtils.XMLINPUTFACTORY
|
||||||
|
.createXMLStreamReader(new StringReader(getCommand(urlQryActiveApp)));
|
||||||
ActiveApp activeApp = (ActiveApp) unmarshaller
|
ActiveApp activeApp = (ActiveApp) unmarshaller
|
||||||
.unmarshal(new StringReader(getCommand(urlQryActiveApp)));
|
.unmarshal(xsr));
|
||||||
if (activeApp != null) {
|
if (activeApp != null) {
|
||||||
return activeApp;
|
return activeApp;
|
||||||
}
|
}
|
||||||
|
@ -143,14 +149,16 @@ public class RokuCommunicator {
|
||||||
if (ctx != null) {
|
if (ctx != null) {
|
||||||
Unmarshaller unmarshaller = ctx.createUnmarshaller();
|
Unmarshaller unmarshaller = ctx.createUnmarshaller();
|
||||||
if (unmarshaller != null) {
|
if (unmarshaller != null) {
|
||||||
Apps appList = (Apps) unmarshaller.unmarshal(new StringReader(getCommand(urlQryApps)));
|
XMLStreamReader xsr = JAXBUtils.XMLINPUTFACTORY
|
||||||
|
.createXMLStreamReader(new StringReader(getCommand(urlQryApps)));
|
||||||
|
Apps appList = (Apps) unmarshaller.unmarshal(xsr);
|
||||||
if (appList != null) {
|
if (appList != null) {
|
||||||
return appList.getApp();
|
return appList.getApp();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
throw new RokuHttpException("No AppList model in response");
|
throw new RokuHttpException("No AppList model in response");
|
||||||
} catch (JAXBException e) {
|
} catch (JAXBException | XMLStreamException e) {
|
||||||
throw new RokuHttpException("Exception creating AppList Unmarshaller: " + e.getLocalizedMessage());
|
throw new RokuHttpException("Exception creating AppList Unmarshaller: " + e.getLocalizedMessage());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -167,14 +175,16 @@ public class RokuCommunicator {
|
||||||
if (ctx != null) {
|
if (ctx != null) {
|
||||||
Unmarshaller unmarshaller = ctx.createUnmarshaller();
|
Unmarshaller unmarshaller = ctx.createUnmarshaller();
|
||||||
if (unmarshaller != null) {
|
if (unmarshaller != null) {
|
||||||
Player playerInfo = (Player) unmarshaller.unmarshal(new StringReader(getCommand(urlQryPlayer)));
|
XMLStreamReader xsr = JAXBUtils.XMLINPUTFACTORY
|
||||||
|
.createXMLStreamReader(new StringReader(getCommand(urlQryPlayer)));
|
||||||
|
Player playerInfo = (Player) unmarshaller.unmarshal(xsr);
|
||||||
if (playerInfo != null) {
|
if (playerInfo != null) {
|
||||||
return playerInfo;
|
return playerInfo;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
throw new RokuHttpException("No Player info model in response");
|
throw new RokuHttpException("No Player info model in response");
|
||||||
} catch (JAXBException e) {
|
} catch (JAXBException | XMLStreamException e) {
|
||||||
throw new RokuHttpException("Exception creating Player info Unmarshaller: " + e.getLocalizedMessage());
|
throw new RokuHttpException("Exception creating Player info Unmarshaller: " + e.getLocalizedMessage());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -81,6 +81,12 @@ public class SamsungTvUtils {
|
||||||
public static @Nullable Document loadXMLFromString(String xml) {
|
public static @Nullable Document loadXMLFromString(String xml) {
|
||||||
try {
|
try {
|
||||||
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
|
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
|
||||||
|
// see https://cheatsheetseries.owasp.org/cheatsheets/XML_External_Entity_Prevention_Cheat_Sheet.html
|
||||||
|
factory.setFeature("http://xml.org/sax/features/external-general-entities", false);
|
||||||
|
factory.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
|
||||||
|
factory.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false);
|
||||||
|
factory.setXIncludeAware(false);
|
||||||
|
factory.setExpandEntityReferences(false);
|
||||||
DocumentBuilder builder = factory.newDocumentBuilder();
|
DocumentBuilder builder = factory.newDocumentBuilder();
|
||||||
InputSource is = new InputSource(new StringReader(xml));
|
InputSource is = new InputSource(new StringReader(xml));
|
||||||
return builder.parse(is);
|
return builder.parse(is);
|
||||||
|
|
|
@ -134,6 +134,7 @@ public class SonosXMLParser {
|
||||||
*/
|
*/
|
||||||
public static @Nullable SonosResourceMetaData getResourceMetaData(String xml) throws SAXException {
|
public static @Nullable SonosResourceMetaData getResourceMetaData(String xml) throws SAXException {
|
||||||
XMLReader reader = XMLReaderFactory.createXMLReader();
|
XMLReader reader = XMLReaderFactory.createXMLReader();
|
||||||
|
reader.setFeature("http://apache.org/xml/features/disallow-doctype-decl", true);
|
||||||
ResourceMetaDataHandler handler = new ResourceMetaDataHandler();
|
ResourceMetaDataHandler handler = new ResourceMetaDataHandler();
|
||||||
reader.setContentHandler(handler);
|
reader.setContentHandler(handler);
|
||||||
try {
|
try {
|
||||||
|
|
|
@ -309,6 +309,8 @@ public class TelldusLiveDeviceController implements DeviceChangeListener, Sensor
|
||||||
// TelldusLiveHandler.logger.info("Devices" + resp.getResponseBody());
|
// TelldusLiveHandler.logger.info("Devices" + resp.getResponseBody());
|
||||||
JAXBContext jc = JAXBContext.newInstance(response);
|
JAXBContext jc = JAXBContext.newInstance(response);
|
||||||
XMLInputFactory xif = XMLInputFactory.newInstance();
|
XMLInputFactory xif = XMLInputFactory.newInstance();
|
||||||
|
xif.setProperty(XMLInputFactory.IS_SUPPORTING_EXTERNAL_ENTITIES, false);
|
||||||
|
xif.setProperty(XMLInputFactory.SUPPORT_DTD, false);
|
||||||
XMLStreamReader xsr = xif.createXMLStreamReader(resp.getResponseBodyAsStream());
|
XMLStreamReader xsr = xif.createXMLStreamReader(resp.getResponseBodyAsStream());
|
||||||
// xsr = new PropertyRenamerDelegate(xsr);
|
// xsr = new PropertyRenamerDelegate(xsr);
|
||||||
|
|
||||||
|
|
|
@ -25,6 +25,9 @@ import java.util.stream.Collectors;
|
||||||
import javax.xml.bind.JAXBContext;
|
import javax.xml.bind.JAXBContext;
|
||||||
import javax.xml.bind.JAXBException;
|
import javax.xml.bind.JAXBException;
|
||||||
import javax.xml.bind.Unmarshaller;
|
import javax.xml.bind.Unmarshaller;
|
||||||
|
import javax.xml.stream.XMLInputFactory;
|
||||||
|
import javax.xml.stream.XMLStreamException;
|
||||||
|
import javax.xml.stream.XMLStreamReader;
|
||||||
import javax.xml.transform.stream.StreamSource;
|
import javax.xml.transform.stream.StreamSource;
|
||||||
|
|
||||||
import org.eclipse.jdt.annotation.NonNullByDefault;
|
import org.eclipse.jdt.annotation.NonNullByDefault;
|
||||||
|
@ -64,8 +67,12 @@ public class Tr064PhonebookImpl implements Phonebook {
|
||||||
InputStream xml = new ByteArrayInputStream(contentResponse.getContent());
|
InputStream xml = new ByteArrayInputStream(contentResponse.getContent());
|
||||||
|
|
||||||
JAXBContext context = JAXBContext.newInstance(PhonebooksType.class);
|
JAXBContext context = JAXBContext.newInstance(PhonebooksType.class);
|
||||||
|
XMLInputFactory xif = XMLInputFactory.newFactory();
|
||||||
|
xif.setProperty(XMLInputFactory.IS_SUPPORTING_EXTERNAL_ENTITIES, false);
|
||||||
|
xif.setProperty(XMLInputFactory.SUPPORT_DTD, false);
|
||||||
|
XMLStreamReader xsr = xif.createXMLStreamReader(new StreamSource(xml));
|
||||||
Unmarshaller um = context.createUnmarshaller();
|
Unmarshaller um = context.createUnmarshaller();
|
||||||
PhonebooksType phonebooksType = um.unmarshal(new StreamSource(xml), PhonebooksType.class).getValue();
|
PhonebooksType phonebooksType = um.unmarshal(xsr, PhonebooksType.class).getValue();
|
||||||
|
|
||||||
phonebookName = phonebooksType.getPhonebook().getName();
|
phonebookName = phonebooksType.getPhonebook().getName();
|
||||||
|
|
||||||
|
@ -76,7 +83,7 @@ public class Tr064PhonebookImpl implements Phonebook {
|
||||||
this::mergeSameContactNames));
|
this::mergeSameContactNames));
|
||||||
}).collect(HashMap::new, HashMap::putAll, HashMap::putAll);
|
}).collect(HashMap::new, HashMap::putAll, HashMap::putAll);
|
||||||
logger.debug("Downloaded phonebook {}: {}", phonebookName, phonebook);
|
logger.debug("Downloaded phonebook {}: {}", phonebookName, phonebook);
|
||||||
} catch (JAXBException | InterruptedException | ExecutionException | TimeoutException e) {
|
} catch (JAXBException | InterruptedException | ExecutionException | TimeoutException | XMLStreamException e) {
|
||||||
logger.warn("Failed to get phonebook with URL {}:", phonebookUrl, e);
|
logger.warn("Failed to get phonebook with URL {}:", phonebookUrl, e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -18,7 +18,12 @@ import java.io.ByteArrayInputStream;
|
||||||
import java.io.InputStream;
|
import java.io.InputStream;
|
||||||
import java.lang.reflect.Field;
|
import java.lang.reflect.Field;
|
||||||
import java.time.Duration;
|
import java.time.Duration;
|
||||||
import java.util.*;
|
import java.util.Collections;
|
||||||
|
import java.util.HashSet;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.Optional;
|
||||||
|
import java.util.Set;
|
||||||
import java.util.concurrent.ExecutionException;
|
import java.util.concurrent.ExecutionException;
|
||||||
import java.util.concurrent.TimeUnit;
|
import java.util.concurrent.TimeUnit;
|
||||||
import java.util.concurrent.TimeoutException;
|
import java.util.concurrent.TimeoutException;
|
||||||
|
@ -31,6 +36,9 @@ import javax.xml.bind.JAXBException;
|
||||||
import javax.xml.bind.Unmarshaller;
|
import javax.xml.bind.Unmarshaller;
|
||||||
import javax.xml.soap.SOAPException;
|
import javax.xml.soap.SOAPException;
|
||||||
import javax.xml.soap.SOAPMessage;
|
import javax.xml.soap.SOAPMessage;
|
||||||
|
import javax.xml.stream.XMLInputFactory;
|
||||||
|
import javax.xml.stream.XMLStreamException;
|
||||||
|
import javax.xml.stream.XMLStreamReader;
|
||||||
import javax.xml.transform.stream.StreamSource;
|
import javax.xml.transform.stream.StreamSource;
|
||||||
|
|
||||||
import org.eclipse.jdt.annotation.NonNullByDefault;
|
import org.eclipse.jdt.annotation.NonNullByDefault;
|
||||||
|
@ -49,7 +57,11 @@ import org.openhab.binding.tr064.internal.dto.config.ChannelTypeDescription;
|
||||||
import org.openhab.binding.tr064.internal.dto.config.ChannelTypeDescriptions;
|
import org.openhab.binding.tr064.internal.dto.config.ChannelTypeDescriptions;
|
||||||
import org.openhab.binding.tr064.internal.dto.config.ParameterType;
|
import org.openhab.binding.tr064.internal.dto.config.ParameterType;
|
||||||
import org.openhab.binding.tr064.internal.dto.scpd.root.SCPDServiceType;
|
import org.openhab.binding.tr064.internal.dto.scpd.root.SCPDServiceType;
|
||||||
import org.openhab.binding.tr064.internal.dto.scpd.service.*;
|
import org.openhab.binding.tr064.internal.dto.scpd.service.SCPDActionType;
|
||||||
|
import org.openhab.binding.tr064.internal.dto.scpd.service.SCPDArgumentType;
|
||||||
|
import org.openhab.binding.tr064.internal.dto.scpd.service.SCPDDirection;
|
||||||
|
import org.openhab.binding.tr064.internal.dto.scpd.service.SCPDScpdType;
|
||||||
|
import org.openhab.binding.tr064.internal.dto.scpd.service.SCPDStateVariableType;
|
||||||
import org.openhab.core.cache.ExpiringCacheMap;
|
import org.openhab.core.cache.ExpiringCacheMap;
|
||||||
import org.openhab.core.thing.ChannelUID;
|
import org.openhab.core.thing.ChannelUID;
|
||||||
import org.openhab.core.thing.Thing;
|
import org.openhab.core.thing.Thing;
|
||||||
|
@ -76,18 +88,21 @@ public class Util {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* read the channel config from the resource file (static initialization)
|
* read the channel config from the resource file (static initialization)
|
||||||
*
|
*
|
||||||
* @return a list of all available channel configurations
|
* @return a list of all available channel configurations
|
||||||
*/
|
*/
|
||||||
public static List<ChannelTypeDescription> readXMLChannelConfig() {
|
public static List<ChannelTypeDescription> readXMLChannelConfig() {
|
||||||
try {
|
try {
|
||||||
InputStream resource = Thread.currentThread().getContextClassLoader().getResourceAsStream("channels.xml");
|
InputStream resource = Thread.currentThread().getContextClassLoader().getResourceAsStream("channels.xml");
|
||||||
JAXBContext context = JAXBContext.newInstance(ChannelTypeDescriptions.class);
|
JAXBContext context = JAXBContext.newInstance(ChannelTypeDescriptions.class);
|
||||||
|
XMLInputFactory xif = XMLInputFactory.newFactory();
|
||||||
|
xif.setProperty(XMLInputFactory.IS_SUPPORTING_EXTERNAL_ENTITIES, false);
|
||||||
|
xif.setProperty(XMLInputFactory.SUPPORT_DTD, false);
|
||||||
|
XMLStreamReader xsr = xif.createXMLStreamReader(new StreamSource(resource));
|
||||||
Unmarshaller um = context.createUnmarshaller();
|
Unmarshaller um = context.createUnmarshaller();
|
||||||
JAXBElement<ChannelTypeDescriptions> root = um.unmarshal(new StreamSource(resource),
|
JAXBElement<ChannelTypeDescriptions> root = um.unmarshal(xsr, ChannelTypeDescriptions.class);
|
||||||
ChannelTypeDescriptions.class);
|
|
||||||
return root.getValue().getChannel();
|
return root.getValue().getChannel();
|
||||||
} catch (JAXBException e) {
|
} catch (JAXBException | XMLStreamException e) {
|
||||||
LOGGER.warn("Failed to read channel definitions", e);
|
LOGGER.warn("Failed to read channel definitions", e);
|
||||||
return List.of();
|
return List.of();
|
||||||
}
|
}
|
||||||
|
@ -95,7 +110,7 @@ public class Util {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Extract an argument from an SCPD action definition
|
* Extract an argument from an SCPD action definition
|
||||||
*
|
*
|
||||||
* @param scpdAction the action object
|
* @param scpdAction the action object
|
||||||
* @param argumentName the argument's name
|
* @param argumentName the argument's name
|
||||||
* @param direction the direction (in or out)
|
* @param direction the direction (in or out)
|
||||||
|
@ -114,7 +129,7 @@ public class Util {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Extract the related state variable from the service root for a given argument
|
* Extract the related state variable from the service root for a given argument
|
||||||
*
|
*
|
||||||
* @param serviceRoot the service root object
|
* @param serviceRoot the service root object
|
||||||
* @param scpdArgument the argument object
|
* @param scpdArgument the argument object
|
||||||
* @return the related state variable object for this argument
|
* @return the related state variable object for this argument
|
||||||
|
@ -130,7 +145,7 @@ public class Util {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Extract an action from the service root
|
* Extract an action from the service root
|
||||||
*
|
*
|
||||||
* @param serviceRoot the service root object
|
* @param serviceRoot the service root object
|
||||||
* @param actionName the action name
|
* @param actionName the action name
|
||||||
* @param actionType "Get-Action" or "Set-Action" (for exception string only)
|
* @param actionType "Get-Action" or "Set-Action" (for exception string only)
|
||||||
|
@ -338,14 +353,18 @@ public class Util {
|
||||||
InputStream xml = new ByteArrayInputStream(response);
|
InputStream xml = new ByteArrayInputStream(response);
|
||||||
|
|
||||||
JAXBContext context = JAXBContext.newInstance(clazz);
|
JAXBContext context = JAXBContext.newInstance(clazz);
|
||||||
|
XMLInputFactory xif = XMLInputFactory.newFactory();
|
||||||
|
xif.setProperty(XMLInputFactory.IS_SUPPORTING_EXTERNAL_ENTITIES, false);
|
||||||
|
xif.setProperty(XMLInputFactory.SUPPORT_DTD, false);
|
||||||
|
XMLStreamReader xsr = xif.createXMLStreamReader(new StreamSource(xml));
|
||||||
Unmarshaller um = context.createUnmarshaller();
|
Unmarshaller um = context.createUnmarshaller();
|
||||||
T newValue = um.unmarshal(new StreamSource(xml), clazz).getValue();
|
T newValue = um.unmarshal(xsr, clazz).getValue();
|
||||||
LOGGER.trace("Storing in cache {}", newValue);
|
LOGGER.trace("Storing in cache {}", newValue);
|
||||||
return newValue;
|
return newValue;
|
||||||
} catch (ExecutionException | InterruptedException | TimeoutException e) {
|
} catch (ExecutionException | InterruptedException | TimeoutException e) {
|
||||||
LOGGER.debug("HTTP Failed to GET uri '{}': {}", uri, e.getMessage());
|
LOGGER.debug("HTTP Failed to GET uri '{}': {}", uri, e.getMessage());
|
||||||
throw new IllegalArgumentException();
|
throw new IllegalArgumentException();
|
||||||
} catch (JAXBException e) {
|
} catch (JAXBException | XMLStreamException e) {
|
||||||
LOGGER.debug("Unmarshalling failed: {}", e.getMessage());
|
LOGGER.debug("Unmarshalling failed: {}", e.getMessage());
|
||||||
throw new IllegalArgumentException();
|
throw new IllegalArgumentException();
|
||||||
}
|
}
|
||||||
|
|
|
@ -79,6 +79,9 @@ public class UpnpXMLParser {
|
||||||
try {
|
try {
|
||||||
SAXParserFactory factory = SAXParserFactory.newInstance();
|
SAXParserFactory factory = SAXParserFactory.newInstance();
|
||||||
SAXParser saxParser = factory.newSAXParser();
|
SAXParser saxParser = factory.newSAXParser();
|
||||||
|
factory.setFeature("https://xml.org/sax/features/external-general-entities", false);
|
||||||
|
saxParser.getXMLReader().setFeature("https://xml.org/sax/features/external-general-entities", false);
|
||||||
|
factory.setFeature("https://apache.org/xml/features/disallow-doctype-decl", true);
|
||||||
saxParser.parse(new InputSource(new StringReader(xml)), handler);
|
saxParser.parse(new InputSource(new StringReader(xml)), handler);
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
// This should never happen - we're not performing I/O!
|
// This should never happen - we're not performing I/O!
|
||||||
|
@ -135,6 +138,9 @@ public class UpnpXMLParser {
|
||||||
try {
|
try {
|
||||||
SAXParserFactory factory = SAXParserFactory.newInstance();
|
SAXParserFactory factory = SAXParserFactory.newInstance();
|
||||||
SAXParser saxParser = factory.newSAXParser();
|
SAXParser saxParser = factory.newSAXParser();
|
||||||
|
factory.setFeature("https://xml.org/sax/features/external-general-entities", false);
|
||||||
|
saxParser.getXMLReader().setFeature("https://xml.org/sax/features/external-general-entities", false);
|
||||||
|
factory.setFeature("https://apache.org/xml/features/disallow-doctype-decl", true);
|
||||||
saxParser.parse(new InputSource(new StringReader(xml)), handler);
|
saxParser.parse(new InputSource(new StringReader(xml)), handler);
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
// This should never happen - we're not performing I/O!
|
// This should never happen - we're not performing I/O!
|
||||||
|
@ -179,6 +185,9 @@ public class UpnpXMLParser {
|
||||||
try {
|
try {
|
||||||
SAXParserFactory factory = SAXParserFactory.newInstance();
|
SAXParserFactory factory = SAXParserFactory.newInstance();
|
||||||
SAXParser saxParser = factory.newSAXParser();
|
SAXParser saxParser = factory.newSAXParser();
|
||||||
|
factory.setFeature("https://xml.org/sax/features/external-general-entities", false);
|
||||||
|
saxParser.getXMLReader().setFeature("https://xml.org/sax/features/external-general-entities", false);
|
||||||
|
factory.setFeature("https://apache.org/xml/features/disallow-doctype-decl", true);
|
||||||
saxParser.parse(new InputSource(new StringReader(xml)), handler);
|
saxParser.parse(new InputSource(new StringReader(xml)), handler);
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
// This should never happen - we're not performing I/O!
|
// This should never happen - we're not performing I/O!
|
||||||
|
|
|
@ -250,6 +250,7 @@ public class VitotronicBridgeHandler extends BaseBridgeHandler {
|
||||||
logger.trace("Start Background Thread for recieving data from adapter");
|
logger.trace("Start Background Thread for recieving data from adapter");
|
||||||
try {
|
try {
|
||||||
XMLReader xmlReader = XMLReaderFactory.createXMLReader();
|
XMLReader xmlReader = XMLReaderFactory.createXMLReader();
|
||||||
|
xmlReader.setFeature("http://apache.org/xml/features/disallow-doctype-decl", true);
|
||||||
xmlReader.setContentHandler(new XmlHandler());
|
xmlReader.setContentHandler(new XmlHandler());
|
||||||
logger.trace("Start Parser for optolink adapter");
|
logger.trace("Start Parser for optolink adapter");
|
||||||
xmlReader.parse(new InputSource(inStream));
|
xmlReader.parse(new InputSource(inStream));
|
||||||
|
|
|
@ -156,6 +156,13 @@ public class WemoLinkDiscoveryService extends AbstractDiscoveryService implement
|
||||||
|
|
||||||
// Build parser for received <DeviceList>
|
// Build parser for received <DeviceList>
|
||||||
DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
|
DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
|
||||||
|
// see
|
||||||
|
// https://cheatsheetseries.owasp.org/cheatsheets/XML_External_Entity_Prevention_Cheat_Sheet.html
|
||||||
|
dbf.setFeature("http://xml.org/sax/features/external-general-entities", false);
|
||||||
|
dbf.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
|
||||||
|
dbf.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false);
|
||||||
|
dbf.setXIncludeAware(false);
|
||||||
|
dbf.setExpandEntityReferences(false);
|
||||||
DocumentBuilder db = dbf.newDocumentBuilder();
|
DocumentBuilder db = dbf.newDocumentBuilder();
|
||||||
InputSource is = new InputSource();
|
InputSource is = new InputSource();
|
||||||
is.setCharacterStream(new StringReader(stringParser));
|
is.setCharacterStream(new StringReader(stringParser));
|
||||||
|
|
|
@ -290,6 +290,13 @@ public class WemoCoffeeHandler extends AbstractWemoHandler implements UpnpIOPart
|
||||||
stringParser = "<data>" + stringParser + "</data>";
|
stringParser = "<data>" + stringParser + "</data>";
|
||||||
|
|
||||||
DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
|
DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
|
||||||
|
// see
|
||||||
|
// https://cheatsheetseries.owasp.org/cheatsheets/XML_External_Entity_Prevention_Cheat_Sheet.html
|
||||||
|
dbf.setFeature("http://xml.org/sax/features/external-general-entities", false);
|
||||||
|
dbf.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
|
||||||
|
dbf.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false);
|
||||||
|
dbf.setXIncludeAware(false);
|
||||||
|
dbf.setExpandEntityReferences(false);
|
||||||
DocumentBuilder db = dbf.newDocumentBuilder();
|
DocumentBuilder db = dbf.newDocumentBuilder();
|
||||||
InputSource is = new InputSource();
|
InputSource is = new InputSource();
|
||||||
is.setCharacterStream(new StringReader(stringParser));
|
is.setCharacterStream(new StringReader(stringParser));
|
||||||
|
|
|
@ -359,6 +359,13 @@ public class WemoHolmesHandler extends AbstractWemoHandler implements UpnpIOPart
|
||||||
stringParser = "<data>" + stringParser + "</data>";
|
stringParser = "<data>" + stringParser + "</data>";
|
||||||
|
|
||||||
DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
|
DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
|
||||||
|
// see
|
||||||
|
// https://cheatsheetseries.owasp.org/cheatsheets/XML_External_Entity_Prevention_Cheat_Sheet.html
|
||||||
|
dbf.setFeature("http://xml.org/sax/features/external-general-entities", false);
|
||||||
|
dbf.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
|
||||||
|
dbf.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false);
|
||||||
|
dbf.setXIncludeAware(false);
|
||||||
|
dbf.setExpandEntityReferences(false);
|
||||||
DocumentBuilder db = dbf.newDocumentBuilder();
|
DocumentBuilder db = dbf.newDocumentBuilder();
|
||||||
InputSource is = new InputSource();
|
InputSource is = new InputSource();
|
||||||
is.setCharacterStream(new StringReader(stringParser));
|
is.setCharacterStream(new StringReader(stringParser));
|
||||||
|
|
|
@ -222,6 +222,13 @@ public class WemoMakerHandler extends AbstractWemoHandler implements UpnpIOParti
|
||||||
stringParser = "<data>" + stringParser + "</data>";
|
stringParser = "<data>" + stringParser + "</data>";
|
||||||
|
|
||||||
DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
|
DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
|
||||||
|
// see
|
||||||
|
// https://cheatsheetseries.owasp.org/cheatsheets/XML_External_Entity_Prevention_Cheat_Sheet.html
|
||||||
|
dbf.setFeature("http://xml.org/sax/features/external-general-entities", false);
|
||||||
|
dbf.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
|
||||||
|
dbf.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false);
|
||||||
|
dbf.setXIncludeAware(false);
|
||||||
|
dbf.setExpandEntityReferences(false);
|
||||||
DocumentBuilder db = dbf.newDocumentBuilder();
|
DocumentBuilder db = dbf.newDocumentBuilder();
|
||||||
InputSource is = new InputSource();
|
InputSource is = new InputSource();
|
||||||
is.setCharacterStream(new StringReader(stringParser));
|
is.setCharacterStream(new StringReader(stringParser));
|
||||||
|
|
|
@ -173,7 +173,13 @@ public class XMLUtils {
|
||||||
: "<?xml version=\"1.0\" encoding=\"utf-8\"?>" + message;
|
: "<?xml version=\"1.0\" encoding=\"utf-8\"?>" + message;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
return XMLUtils.dbf.newDocumentBuilder().parse(new InputSource(new StringReader(response)));
|
// see https://cheatsheetseries.owasp.org/cheatsheets/XML_External_Entity_Prevention_Cheat_Sheet.html
|
||||||
|
dbf.setFeature("http://xml.org/sax/features/external-general-entities", false);
|
||||||
|
dbf.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
|
||||||
|
dbf.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false);
|
||||||
|
dbf.setXIncludeAware(false);
|
||||||
|
dbf.setExpandEntityReferences(false);
|
||||||
|
return dbf.newDocumentBuilder().parse(new InputSource(new StringReader(response)));
|
||||||
} catch (SAXException | ParserConfigurationException e) {
|
} catch (SAXException | ParserConfigurationException e) {
|
||||||
throw new ReceivedMessageParseException(e);
|
throw new ReceivedMessageParseException(e);
|
||||||
}
|
}
|
||||||
|
|
|
@ -55,6 +55,12 @@ public class XPathTransformationService implements TransformationService {
|
||||||
|
|
||||||
try {
|
try {
|
||||||
DocumentBuilderFactory domFactory = DocumentBuilderFactory.newInstance();
|
DocumentBuilderFactory domFactory = DocumentBuilderFactory.newInstance();
|
||||||
|
// see https://cheatsheetseries.owasp.org/cheatsheets/XML_External_Entity_Prevention_Cheat_Sheet.html
|
||||||
|
domFactory.setFeature("http://xml.org/sax/features/external-general-entities", false);
|
||||||
|
domFactory.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
|
||||||
|
domFactory.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false);
|
||||||
|
domFactory.setXIncludeAware(false);
|
||||||
|
domFactory.setExpandEntityReferences(false);
|
||||||
domFactory.setNamespaceAware(true);
|
domFactory.setNamespaceAware(true);
|
||||||
domFactory.setValidating(false);
|
domFactory.setValidating(false);
|
||||||
DocumentBuilder builder = domFactory.newDocumentBuilder();
|
DocumentBuilder builder = domFactory.newDocumentBuilder();
|
||||||
|
|
Loading…
Reference in New Issue