[java-opensaml] branch master updated: OSJ-210: XMLObjectSupport.unmarshallFromReader throws ArrayOutOfBoundsException with invalid version
Brent Putman
putmanb at georgetown.edu
Wed Jun 7 16:02:10 EDT 2017
This is an automated email from the git hooks/post-receive script.
putmanb pushed a commit to branch master
in repository java-opensaml.
View the commit online:
http://git.shibboleth.net/view/?p=java-opensaml.git;a=commit;h=e7a77a0b05f732d74337173be737c4c2328dd043
The following commit(s) were added to refs/heads/master by this push:
new e7a77a0 OSJ-210: XMLObjectSupport.unmarshallFromReader throws ArrayOutOfBoundsException with invalid version
e7a77a0 is described below
commit e7a77a0b05f732d74337173be737c4c2328dd043
Author: Brent Putman <putmanb at georgetown.edu>
AuthorDate: Wed Jun 7 15:20:51 2017 -0400
OSJ-210: XMLObjectSupport.unmarshallFromReader throws
ArrayOutOfBoundsException with invalid version
Specifically handle invalid SAMLVersion parsing in SAML unmarshaller
base class.
Handle XMLObjectSupport unmarshalling more generally by catching all
unchecked exceptions.
---
.../opensaml/core/xml/util/XMLObjectSupport.java | 80 ++++++++++++----------
.../opensaml/core/xml/XMLObjectBaseTestCase.java | 46 ++++++++++---
.../common/AbstractSAMLObjectUnmarshaller.java | 19 +++++
.../saml2/core/impl/AssertionUnmarshaller.java | 3 +-
.../core/impl/RequestAbstractTypeUnmarshaller.java | 3 +-
.../core/impl/StatusResponseTypeUnmarshaller.java | 3 +-
.../saml/saml2/core/impl/AssertionTest.java | 9 +++
.../saml/saml2/core/impl/AuthnRequestTest.java | 9 +++
.../saml/saml2/core/impl/ResponseTest.java | 9 +++
.../saml2/core/impl/AssertionBadSAMLVersion.xml | 2 +
.../saml2/core/impl/AuthnRequestBadSAMLVersion.xml | 2 +
.../saml2/core/impl/ResponseBadSAMLVersion.xml | 2 +
12 files changed, 134 insertions(+), 53 deletions(-)
diff --git a/opensaml-core/src/main/java/org/opensaml/core/xml/util/XMLObjectSupport.java b/opensaml-core/src/main/java/org/opensaml/core/xml/util/XMLObjectSupport.java
index ec17229..b00d0cd 100644
--- a/opensaml-core/src/main/java/org/opensaml/core/xml/util/XMLObjectSupport.java
+++ b/opensaml-core/src/main/java/org/opensaml/core/xml/util/XMLObjectSupport.java
@@ -226,28 +226,32 @@ public final class XMLObjectSupport {
Logger log = getLogger();
log.debug("Parsing InputStream into DOM document");
- Document messageDoc = parserPool.parse(inputStream);
- Element messageElem = messageDoc.getDocumentElement();
+ try {
+ Document messageDoc = parserPool.parse(inputStream);
+ Element messageElem = messageDoc.getDocumentElement();
- if (log.isTraceEnabled()) {
- log.trace("Resultant DOM message was:");
- log.trace(SerializeSupport.nodeToString(messageElem));
- }
+ if (log.isTraceEnabled()) {
+ log.trace("Resultant DOM message was:");
+ log.trace(SerializeSupport.nodeToString(messageElem));
+ }
- log.debug("Unmarshalling DOM parsed from InputStream");
- Unmarshaller unmarshaller = getUnmarshaller(messageElem);
- if (unmarshaller == null) {
- log.error("Unable to unmarshall InputStream, no unmarshaller registered for element "
- + QNameSupport.getNodeQName(messageElem));
- throw new UnmarshallingException(
- "Unable to unmarshall InputStream, no unmarshaller registered for element "
- + QNameSupport.getNodeQName(messageElem));
- }
+ log.debug("Unmarshalling DOM parsed from InputStream");
+ Unmarshaller unmarshaller = getUnmarshaller(messageElem);
+ if (unmarshaller == null) {
+ log.error("Unable to unmarshall InputStream, no unmarshaller registered for element "
+ + QNameSupport.getNodeQName(messageElem));
+ throw new UnmarshallingException(
+ "Unable to unmarshall InputStream, no unmarshaller registered for element "
+ + QNameSupport.getNodeQName(messageElem));
+ }
- XMLObject message = unmarshaller.unmarshall(messageElem);
+ XMLObject message = unmarshaller.unmarshall(messageElem);
- log.debug("InputStream succesfully unmarshalled");
- return message;
+ log.debug("InputStream succesfully unmarshalled");
+ return message;
+ } catch (RuntimeException e) {
+ throw new UnmarshallingException("Fatal error unmarshalling XMLObject", e);
+ }
}
/**
@@ -265,28 +269,32 @@ public final class XMLObjectSupport {
log.debug("Parsing Reader into DOM document");
- Document messageDoc = parserPool.parse(reader);
- Element messageElem = messageDoc.getDocumentElement();
+ try {
+ Document messageDoc = parserPool.parse(reader);
+ Element messageElem = messageDoc.getDocumentElement();
- if (log.isTraceEnabled()) {
- log.trace("Resultant DOM message was:");
- log.trace(SerializeSupport.nodeToString(messageElem));
- }
+ if (log.isTraceEnabled()) {
+ log.trace("Resultant DOM message was:");
+ log.trace(SerializeSupport.nodeToString(messageElem));
+ }
- log.debug("Unmarshalling DOM parsed from Reader");
- Unmarshaller unmarshaller = getUnmarshaller(messageElem);
- if (unmarshaller == null) {
- log.error("Unable to unmarshall Reader, no unmarshaller registered for element "
- + QNameSupport.getNodeQName(messageElem));
- throw new UnmarshallingException(
- "Unable to unmarshall Reader, no unmarshaller registered for element "
- + QNameSupport.getNodeQName(messageElem));
- }
+ log.debug("Unmarshalling DOM parsed from Reader");
+ Unmarshaller unmarshaller = getUnmarshaller(messageElem);
+ if (unmarshaller == null) {
+ log.error("Unable to unmarshall Reader, no unmarshaller registered for element "
+ + QNameSupport.getNodeQName(messageElem));
+ throw new UnmarshallingException(
+ "Unable to unmarshall Reader, no unmarshaller registered for element "
+ + QNameSupport.getNodeQName(messageElem));
+ }
- XMLObject message = unmarshaller.unmarshall(messageElem);
+ XMLObject message = unmarshaller.unmarshall(messageElem);
- log.debug("Reader succesfully unmarshalled");
- return message;
+ log.debug("Reader succesfully unmarshalled");
+ return message;
+ } catch (RuntimeException e) {
+ throw new UnmarshallingException("Fatal error unmarshalling XMLObject", e);
+ }
}
/**
diff --git a/opensaml-core/src/test/java/org/opensaml/core/xml/XMLObjectBaseTestCase.java b/opensaml-core/src/test/java/org/opensaml/core/xml/XMLObjectBaseTestCase.java
index 441f55e..047678a 100644
--- a/opensaml-core/src/test/java/org/opensaml/core/xml/XMLObjectBaseTestCase.java
+++ b/opensaml-core/src/test/java/org/opensaml/core/xml/XMLObjectBaseTestCase.java
@@ -29,16 +29,7 @@ import javax.xml.datatype.DatatypeConfigurationException;
import javax.xml.datatype.DatatypeFactory;
import javax.xml.namespace.QName;
-import net.shibboleth.utilities.java.support.xml.AttributeSupport;
-import net.shibboleth.utilities.java.support.xml.ParserPool;
-import net.shibboleth.utilities.java.support.xml.QNameSupport;
-import net.shibboleth.utilities.java.support.xml.SerializeSupport;
-import net.shibboleth.utilities.java.support.xml.XMLParserException;
-
import org.custommonkey.xmlunit.Diff;
-
-import net.shibboleth.utilities.java.support.xml.XMLAssertTestNG;
-
import org.custommonkey.xmlunit.XMLUnit;
import org.opensaml.core.OpenSAMLInitBaseTestCase;
import org.opensaml.core.xml.config.XMLObjectProviderRegistrySupport;
@@ -58,6 +49,13 @@ import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.Node;
+import net.shibboleth.utilities.java.support.xml.AttributeSupport;
+import net.shibboleth.utilities.java.support.xml.ParserPool;
+import net.shibboleth.utilities.java.support.xml.QNameSupport;
+import net.shibboleth.utilities.java.support.xml.SerializeSupport;
+import net.shibboleth.utilities.java.support.xml.XMLAssertTestNG;
+import net.shibboleth.utilities.java.support.xml.XMLParserException;
+
/**
* Base test case class for tests that operate on XMLObjects.
*/
@@ -178,6 +176,24 @@ public abstract class XMLObjectBaseTestCase extends OpenSAMLInitBaseTestCase {
*/
protected <T extends XMLObject> T unmarshallElement(String elementFile) {
try {
+ return unmarshallElement(elementFile, false);
+ } catch (XMLParserException | UnmarshallingException e) {
+ // Won't happen due to flag being passed
+ Assert.fail("Unable to parse or unmarshall element file " + elementFile + ": " + e);
+ return null;
+ }
+ }
+
+ /**
+ * Unmarshalls an element file into its XMLObject.
+ *
+ * @param if true, checked exceptions will be thrown, if false then they cause assertion of test failure
+ * @return the XMLObject from the file
+ *
+ */
+ protected <T extends XMLObject> T unmarshallElement(String elementFile, boolean propagateErrors)
+ throws XMLParserException, UnmarshallingException {
+ try {
final Document doc = parseXMLDocument(elementFile);
final Element element = doc.getDocumentElement();
final Unmarshaller unmarshaller = getUnmarshaller(element);
@@ -185,9 +201,17 @@ public abstract class XMLObjectBaseTestCase extends OpenSAMLInitBaseTestCase {
Assert.assertNotNull(object);
return object;
} catch (final XMLParserException e) {
- Assert.fail("Unable to parse element file " + elementFile);
+ if (propagateErrors) {
+ throw e;
+ } else {
+ Assert.fail("Unable to parse element file " + elementFile);
+ }
} catch (final UnmarshallingException e) {
- Assert.fail("Unmarshalling failed when parsing element file " + elementFile + ": " + e);
+ if (propagateErrors) {
+ throw e;
+ } else {
+ Assert.fail("Unmarshalling failed when parsing element file " + elementFile + ": " + e);
+ }
}
return null;
diff --git a/opensaml-saml-api/src/main/java/org/opensaml/saml/common/AbstractSAMLObjectUnmarshaller.java b/opensaml-saml-api/src/main/java/org/opensaml/saml/common/AbstractSAMLObjectUnmarshaller.java
index 65e9463..b387e60 100644
--- a/opensaml-saml-api/src/main/java/org/opensaml/saml/common/AbstractSAMLObjectUnmarshaller.java
+++ b/opensaml-saml-api/src/main/java/org/opensaml/saml/common/AbstractSAMLObjectUnmarshaller.java
@@ -17,9 +17,12 @@
package org.opensaml.saml.common;
+import javax.annotation.Nonnull;
import javax.annotation.concurrent.ThreadSafe;
import org.opensaml.core.xml.io.AbstractXMLObjectUnmarshaller;
+import org.opensaml.core.xml.io.UnmarshallingException;
+import org.w3c.dom.Attr;
/**
* An thread safe abstract unmarshaller. This abstract unmarshaller only works with
@@ -27,5 +30,21 @@ import org.opensaml.core.xml.io.AbstractXMLObjectUnmarshaller;
*/
@ThreadSafe
public abstract class AbstractSAMLObjectUnmarshaller extends AbstractXMLObjectUnmarshaller {
+
+ /**
+ * Parse {@link SAMLVersion} instance from the specified DOM attribute.
+ *
+ * @param attribute the DOM attribute to process
+ * @return the parsed SAMLVersion instance
+ * @throws UnmarshallingException if a SAMLVersion instance could not be successfully parsed
+ */
+ @Nonnull protected SAMLVersion parseSAMLVersion(@Nonnull final Attr attribute) throws UnmarshallingException {
+ try {
+ return SAMLVersion.valueOf(attribute.getValue());
+ } catch (RuntimeException e) {
+ throw new UnmarshallingException(String.format("Could not parse SAMLVersion from DOM attribute value '%s'",
+ attribute.getValue()), e);
+ }
+ }
}
\ No newline at end of file
diff --git a/opensaml-saml-impl/src/main/java/org/opensaml/saml/saml2/core/impl/AssertionUnmarshaller.java b/opensaml-saml-impl/src/main/java/org/opensaml/saml/saml2/core/impl/AssertionUnmarshaller.java
index f573030..172eeec 100644
--- a/opensaml-saml-impl/src/main/java/org/opensaml/saml/saml2/core/impl/AssertionUnmarshaller.java
+++ b/opensaml-saml-impl/src/main/java/org/opensaml/saml/saml2/core/impl/AssertionUnmarshaller.java
@@ -26,7 +26,6 @@ import org.joda.time.chrono.ISOChronology;
import org.opensaml.core.xml.XMLObject;
import org.opensaml.core.xml.io.UnmarshallingException;
import org.opensaml.saml.common.AbstractSAMLObjectUnmarshaller;
-import org.opensaml.saml.common.SAMLVersion;
import org.opensaml.saml.saml2.core.Advice;
import org.opensaml.saml.saml2.core.Assertion;
import org.opensaml.saml.saml2.core.Conditions;
@@ -70,7 +69,7 @@ public class AssertionUnmarshaller extends AbstractSAMLObjectUnmarshaller {
if (attribute.getNamespaceURI() == null) {
if (attribute.getLocalName().equals(Assertion.VERSION_ATTRIB_NAME)) {
- assertion.setVersion(SAMLVersion.valueOf(attribute.getValue()));
+ assertion.setVersion(parseSAMLVersion(attribute));
} else if (attribute.getLocalName().equals(Assertion.ISSUE_INSTANT_ATTRIB_NAME)
&& !Strings.isNullOrEmpty(attribute.getValue())) {
assertion.setIssueInstant(new DateTime(attribute.getValue(), ISOChronology.getInstanceUTC()));
diff --git a/opensaml-saml-impl/src/main/java/org/opensaml/saml/saml2/core/impl/RequestAbstractTypeUnmarshaller.java b/opensaml-saml-impl/src/main/java/org/opensaml/saml/saml2/core/impl/RequestAbstractTypeUnmarshaller.java
index e07cb48..f860210 100644
--- a/opensaml-saml-impl/src/main/java/org/opensaml/saml/saml2/core/impl/RequestAbstractTypeUnmarshaller.java
+++ b/opensaml-saml-impl/src/main/java/org/opensaml/saml/saml2/core/impl/RequestAbstractTypeUnmarshaller.java
@@ -26,7 +26,6 @@ import org.joda.time.chrono.ISOChronology;
import org.opensaml.core.xml.XMLObject;
import org.opensaml.core.xml.io.UnmarshallingException;
import org.opensaml.saml.common.AbstractSAMLObjectUnmarshaller;
-import org.opensaml.saml.common.SAMLVersion;
import org.opensaml.saml.saml2.core.Extensions;
import org.opensaml.saml.saml2.core.Issuer;
import org.opensaml.saml.saml2.core.RequestAbstractType;
@@ -62,7 +61,7 @@ public abstract class RequestAbstractTypeUnmarshaller extends AbstractSAMLObject
if (attribute.getNamespaceURI() == null) {
if (attribute.getLocalName().equals(RequestAbstractType.VERSION_ATTRIB_NAME)) {
- req.setVersion(SAMLVersion.valueOf(attribute.getValue()));
+ req.setVersion(parseSAMLVersion(attribute));
} else if (attribute.getLocalName().equals(RequestAbstractType.ID_ATTRIB_NAME)) {
req.setID(attribute.getValue());
attribute.getOwnerElement().setIdAttributeNode(attribute, true);
diff --git a/opensaml-saml-impl/src/main/java/org/opensaml/saml/saml2/core/impl/StatusResponseTypeUnmarshaller.java b/opensaml-saml-impl/src/main/java/org/opensaml/saml/saml2/core/impl/StatusResponseTypeUnmarshaller.java
index 8ee5695..02433e2 100644
--- a/opensaml-saml-impl/src/main/java/org/opensaml/saml/saml2/core/impl/StatusResponseTypeUnmarshaller.java
+++ b/opensaml-saml-impl/src/main/java/org/opensaml/saml/saml2/core/impl/StatusResponseTypeUnmarshaller.java
@@ -26,7 +26,6 @@ import org.joda.time.chrono.ISOChronology;
import org.opensaml.core.xml.XMLObject;
import org.opensaml.core.xml.io.UnmarshallingException;
import org.opensaml.saml.common.AbstractSAMLObjectUnmarshaller;
-import org.opensaml.saml.common.SAMLVersion;
import org.opensaml.saml.saml2.core.Extensions;
import org.opensaml.saml.saml2.core.Issuer;
import org.opensaml.saml.saml2.core.Status;
@@ -65,7 +64,7 @@ public abstract class StatusResponseTypeUnmarshaller extends AbstractSAMLObjectU
if (attribute.getNamespaceURI() == null) {
if (attribute.getLocalName().equals(StatusResponseType.VERSION_ATTRIB_NAME)) {
- sr.setVersion(SAMLVersion.valueOf(attribute.getValue()));
+ sr.setVersion(parseSAMLVersion(attribute));
} else if (attribute.getLocalName().equals(StatusResponseType.ID_ATTRIB_NAME)) {
sr.setID(attribute.getValue());
attribute.getOwnerElement().setIdAttributeNode(attribute, true);
diff --git a/opensaml-saml-impl/src/test/java/org/opensaml/saml/saml2/core/impl/AssertionTest.java b/opensaml-saml-impl/src/test/java/org/opensaml/saml/saml2/core/impl/AssertionTest.java
index 9a9c7b8..7458939 100644
--- a/opensaml-saml-impl/src/test/java/org/opensaml/saml/saml2/core/impl/AssertionTest.java
+++ b/opensaml-saml-impl/src/test/java/org/opensaml/saml/saml2/core/impl/AssertionTest.java
@@ -18,6 +18,9 @@
package org.opensaml.saml.saml2.core.impl;
import org.testng.annotations.Test;
+
+import net.shibboleth.utilities.java.support.xml.XMLParserException;
+
import org.testng.annotations.BeforeMethod;
import org.testng.Assert;
import javax.xml.namespace.QName;
@@ -25,6 +28,7 @@ import javax.xml.namespace.QName;
import org.joda.time.DateTime;
import org.joda.time.chrono.ISOChronology;
import org.opensaml.core.xml.XMLObjectProviderBaseTestCase;
+import org.opensaml.core.xml.io.UnmarshallingException;
import org.opensaml.saml.common.SAMLVersion;
import org.opensaml.saml.common.xml.SAMLConstants;
import org.opensaml.saml.saml2.core.Advice;
@@ -178,4 +182,9 @@ public class AssertionTest extends XMLObjectProviderBaseTestCase {
assertXMLEquals(expectedChildElementsDOM, assertion);
}
+
+ @Test(expectedExceptions=UnmarshallingException.class)
+ public void testBadSAMLVersion() throws XMLParserException, UnmarshallingException {
+ unmarshallElement("/org/opensaml/saml/saml2/core/impl/AssertionBadSAMLVersion.xml", true);
+ }
}
\ No newline at end of file
diff --git a/opensaml-saml-impl/src/test/java/org/opensaml/saml/saml2/core/impl/AuthnRequestTest.java b/opensaml-saml-impl/src/test/java/org/opensaml/saml/saml2/core/impl/AuthnRequestTest.java
index f5b368d..588b84b 100644
--- a/opensaml-saml-impl/src/test/java/org/opensaml/saml/saml2/core/impl/AuthnRequestTest.java
+++ b/opensaml-saml-impl/src/test/java/org/opensaml/saml/saml2/core/impl/AuthnRequestTest.java
@@ -21,10 +21,14 @@
package org.opensaml.saml.saml2.core.impl;
import org.testng.annotations.Test;
+
+import net.shibboleth.utilities.java.support.xml.XMLParserException;
+
import org.testng.annotations.BeforeMethod;
import org.testng.Assert;
import javax.xml.namespace.QName;
+import org.opensaml.core.xml.io.UnmarshallingException;
import org.opensaml.core.xml.schema.XSBooleanValue;
import org.opensaml.saml.common.xml.SAMLConstants;
import org.opensaml.saml.saml2.core.AuthnRequest;
@@ -239,4 +243,9 @@ public class AuthnRequestTest extends RequestTestBase {
Assert.assertNull(req.isPassiveXSBoolean(), "XSBooleanValue was not null");
}
+ @Test(expectedExceptions=UnmarshallingException.class)
+ public void testBadSAMLVersion() throws XMLParserException, UnmarshallingException {
+ unmarshallElement("/org/opensaml/saml/saml2/core/impl/AuthnRequestBadSAMLVersion.xml", true);
+ }
+
}
\ No newline at end of file
diff --git a/opensaml-saml-impl/src/test/java/org/opensaml/saml/saml2/core/impl/ResponseTest.java b/opensaml-saml-impl/src/test/java/org/opensaml/saml/saml2/core/impl/ResponseTest.java
index a35c595..23880c6 100644
--- a/opensaml-saml-impl/src/test/java/org/opensaml/saml/saml2/core/impl/ResponseTest.java
+++ b/opensaml-saml-impl/src/test/java/org/opensaml/saml/saml2/core/impl/ResponseTest.java
@@ -21,10 +21,14 @@
package org.opensaml.saml.saml2.core.impl;
import org.testng.annotations.Test;
+
+import net.shibboleth.utilities.java.support.xml.XMLParserException;
+
import org.testng.annotations.BeforeMethod;
import org.testng.Assert;
import javax.xml.namespace.QName;
+import org.opensaml.core.xml.io.UnmarshallingException;
import org.opensaml.saml.common.xml.SAMLConstants;
import org.opensaml.saml.saml2.core.Assertion;
import org.opensaml.saml.saml2.core.EncryptedAssertion;
@@ -129,5 +133,10 @@ public class ResponseTest extends StatusResponseTestBase {
Assert.assertEquals(resp.getEncryptedAssertions().size(), expectedNumEncryptedAssertions, "EncryptedAssertion count");
super.helperTestChildElementsUnmarshall(resp);
}
+
+ @Test(expectedExceptions=UnmarshallingException.class)
+ public void testBadSAMLVersion() throws XMLParserException, UnmarshallingException {
+ unmarshallElement("/org/opensaml/saml/saml2/core/impl/ResponseBadSAMLVersion.xml", true);
+ }
}
diff --git a/opensaml-saml-impl/src/test/resources/org/opensaml/saml/saml2/core/impl/AssertionBadSAMLVersion.xml b/opensaml-saml-impl/src/test/resources/org/opensaml/saml/saml2/core/impl/AssertionBadSAMLVersion.xml
new file mode 100644
index 0000000..2d5f21f
--- /dev/null
+++ b/opensaml-saml-impl/src/test/resources/org/opensaml/saml/saml2/core/impl/AssertionBadSAMLVersion.xml
@@ -0,0 +1,2 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<saml2:Assertion xmlns:saml2="urn:oasis:names:tc:SAML:2.0:assertion" IssueInstant="1984-08-26T10:01:30.043Z" Version="2"/>
diff --git a/opensaml-saml-impl/src/test/resources/org/opensaml/saml/saml2/core/impl/AuthnRequestBadSAMLVersion.xml b/opensaml-saml-impl/src/test/resources/org/opensaml/saml/saml2/core/impl/AuthnRequestBadSAMLVersion.xml
new file mode 100644
index 0000000..7257d33
--- /dev/null
+++ b/opensaml-saml-impl/src/test/resources/org/opensaml/saml/saml2/core/impl/AuthnRequestBadSAMLVersion.xml
@@ -0,0 +1,2 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<saml2p:AuthnRequest xmlns:saml2p="urn:oasis:names:tc:SAML:2.0:protocol" ID="abc123" Version="2" IssueInstant="2006-02-21T16:40:00.000Z"/>
diff --git a/opensaml-saml-impl/src/test/resources/org/opensaml/saml/saml2/core/impl/ResponseBadSAMLVersion.xml b/opensaml-saml-impl/src/test/resources/org/opensaml/saml/saml2/core/impl/ResponseBadSAMLVersion.xml
new file mode 100644
index 0000000..6854184
--- /dev/null
+++ b/opensaml-saml-impl/src/test/resources/org/opensaml/saml/saml2/core/impl/ResponseBadSAMLVersion.xml
@@ -0,0 +1,2 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<saml2p:Response xmlns:saml2p="urn:oasis:names:tc:SAML:2.0:protocol" ID="def456" Version="2" IssueInstant="2006-02-21T16:40:00.000Z"/>
--
To stop receiving notification emails like this one, please contact
the administrator of this repository.
More information about the commits
mailing list