commit 48915f05037f5c246878f9b6a6fab78bfcd6c86f
Author: gil <puntogil(a)libero.it>
Date: Thu Dec 4 01:01:28 2014 +0100
- fix for CVE-2014-0363 (rhbz#1093274)
- remove jzlib systemPath in smackx pom
smack-3.2.2-CVE-2014-0363.patch | 505 +++++++++++++++++++++++++++++++++++++++
smack.spec | 27 +--
smackx-3.2.2.pom | 2 -
3 files changed, 515 insertions(+), 19 deletions(-)
---
diff --git a/smack-3.2.2-CVE-2014-0363.patch b/smack-3.2.2-CVE-2014-0363.patch
new file mode 100644
index 0000000..c9a9b6e
--- /dev/null
+++ b/smack-3.2.2-CVE-2014-0363.patch
@@ -0,0 +1,505 @@
+diff -Nru smack_src_3_2_2/source/org/jivesoftware/smack/ConnectionConfiguration.java
smack_src_3_2_2-gil/source/org/jivesoftware/smack/ConnectionConfiguration.java
+--- smack_src_3_2_2/source/org/jivesoftware/smack/ConnectionConfiguration.java 2014-08-21
13:26:03.380514185 +0200
++++
smack_src_3_2_2-gil/source/org/jivesoftware/smack/ConnectionConfiguration.java 2014-08-21
13:25:06.388343812 +0200
+@@ -26,7 +26,6 @@
+ import javax.net.SocketFactory;
+ import javax.net.ssl.HostnameVerifier;
+ import javax.security.auth.callback.CallbackHandler;
+-import java.io.File;
+
+ /**
+ * Configuration to use while establishing the connection to the server. It is possible
to
+@@ -49,17 +48,9 @@
+ private String host;
+ private int port;
+
+- private String truststorePath;
+- private String truststoreType;
+- private String truststorePassword;
+ private String keystorePath;
+ private String keystoreType;
+ private String pkcs11Library;
+- private boolean verifyChainEnabled = false;
+- private boolean verifyRootCAEnabled = false;
+- private boolean selfSignedCertificateEnabled = false;
+- private boolean expiredCertificatesCheckEnabled = false;
+- private boolean notMatchingDomainCheckEnabled = false;
+
+ private boolean compressionEnabled = false;
+
+@@ -185,18 +176,6 @@
+ this.serviceName = serviceName;
+ this.proxy = proxy;
+
+- // Build the default path to the cacert truststore file. By default we are
+- // going to use the file located in $JREHOME/lib/security/cacerts.
+- String javaHome = System.getProperty("java.home");
+- StringBuilder buffer = new StringBuilder();
+- buffer.append(javaHome).append(File.separator).append("lib");
+- buffer.append(File.separator).append("security");
+- buffer.append(File.separator).append("cacerts");
+- truststorePath = buffer.toString();
+- // Set the default store type
+- truststoreType = "jks";
+- // Set the default password of the cacert file that is "changeit"
+- truststorePassword = "changeit";
+ keystorePath = System.getProperty("javax.net.ssl.keyStore");
+ keystoreType = "jks";
+ pkcs11Library = "pkcs11.config";
+@@ -265,66 +244,6 @@
+ }
+
+ /**
+- * Retuns the path to the trust store file. The trust store file contains the root
+- * certificates of several well known CAs. By default, will attempt to use the
+- * the file located in $JREHOME/lib/security/cacerts.
+- *
+- * @return the path to the truststore file.
+- */
+- public String getTruststorePath() {
+- return truststorePath;
+- }
+-
+- /**
+- * Sets the path to the trust store file. The truststore file contains the root
+- * certificates of several well?known CAs. By default Smack is going to use
+- * the file located in $JREHOME/lib/security/cacerts.
+- *
+- * @param truststorePath the path to the truststore file.
+- */
+- public void setTruststorePath(String truststorePath) {
+- this.truststorePath = truststorePath;
+- }
+-
+- /**
+- * Returns the trust store type, or <tt>null</tt> if it's not set.
+- *
+- * @return the trust store type.
+- */
+- public String getTruststoreType() {
+- return truststoreType;
+- }
+-
+- /**
+- * Sets the trust store type.
+- *
+- * @param truststoreType the trust store type.
+- */
+- public void setTruststoreType(String truststoreType) {
+- this.truststoreType = truststoreType;
+- }
+-
+- /**
+- * Returns the password to use to access the trust store file. It is assumed that
all
+- * certificates share the same password in the trust store.
+- *
+- * @return the password to use to access the truststore file.
+- */
+- public String getTruststorePassword() {
+- return truststorePassword;
+- }
+-
+- /**
+- * Sets the password to use to access the trust store file. It is assumed that all
+- * certificates share the same password in the trust store.
+- *
+- * @param truststorePassword the password to use to access the truststore file.
+- */
+- public void setTruststorePassword(String truststorePassword) {
+- this.truststorePassword = truststorePassword;
+- }
+-
+- /**
+ * Retuns the path to the keystore file. The key store file contains the
+ * certificates that may be used to authenticate the client to the server,
+ * in the event the server requests or requires it.
+@@ -385,110 +304,6 @@
+ this.pkcs11Library = pkcs11Library;
+ }
+
+- /**
+- * Returns true if the whole chain of certificates presented by the server are going
to
+- * be checked. By default the certificate chain is not verified.
+- *
+- * @return true if the whole chaing of certificates presented by the server are
going to
+- * be checked.
+- */
+- public boolean isVerifyChainEnabled() {
+- return verifyChainEnabled;
+- }
+-
+- /**
+- * Sets if the whole chain of certificates presented by the server are going to
+- * be checked. By default the certificate chain is not verified.
+- *
+- * @param verifyChainEnabled if the whole chaing of certificates presented by the
server
+- * are going to be checked.
+- */
+- public void setVerifyChainEnabled(boolean verifyChainEnabled) {
+- this.verifyChainEnabled = verifyChainEnabled;
+- }
+-
+- /**
+- * Returns true if root CA checking is going to be done. By default checking is
disabled.
+- *
+- * @return true if root CA checking is going to be done.
+- */
+- public boolean isVerifyRootCAEnabled() {
+- return verifyRootCAEnabled;
+- }
+-
+- /**
+- * Sets if root CA checking is going to be done. By default checking is disabled.
+- *
+- * @param verifyRootCAEnabled if root CA checking is going to be done.
+- */
+- public void setVerifyRootCAEnabled(boolean verifyRootCAEnabled) {
+- this.verifyRootCAEnabled = verifyRootCAEnabled;
+- }
+-
+- /**
+- * Returns true if self-signed certificates are going to be accepted. By default
+- * this option is disabled.
+- *
+- * @return true if self-signed certificates are going to be accepted.
+- */
+- public boolean isSelfSignedCertificateEnabled() {
+- return selfSignedCertificateEnabled;
+- }
+-
+- /**
+- * Sets if self-signed certificates are going to be accepted. By default
+- * this option is disabled.
+- *
+- * @param selfSignedCertificateEnabled if self-signed certificates are going to be
accepted.
+- */
+- public void setSelfSignedCertificateEnabled(boolean selfSignedCertificateEnabled) {
+- this.selfSignedCertificateEnabled = selfSignedCertificateEnabled;
+- }
+-
+- /**
+- * Returns true if certificates presented by the server are going to be checked for
their
+- * validity. By default certificates are not verified.
+- *
+- * @return true if certificates presented by the server are going to be checked for
their
+- * validity.
+- */
+- public boolean isExpiredCertificatesCheckEnabled() {
+- return expiredCertificatesCheckEnabled;
+- }
+-
+- /**
+- * Sets if certificates presented by the server are going to be checked for their
+- * validity. By default certificates are not verified.
+- *
+- * @param expiredCertificatesCheckEnabled if certificates presented by the server
are going
+- * to be checked for their validity.
+- */
+- public void setExpiredCertificatesCheckEnabled(boolean
expiredCertificatesCheckEnabled) {
+- this.expiredCertificatesCheckEnabled = expiredCertificatesCheckEnabled;
+- }
+-
+- /**
+- * Returns true if certificates presented by the server are going to be checked for
their
+- * domain. By default certificates are not verified.
+- *
+- * @return true if certificates presented by the server are going to be checked for
their
+- * domain.
+- */
+- public boolean isNotMatchingDomainCheckEnabled() {
+- return notMatchingDomainCheckEnabled;
+- }
+-
+- /**
+- * Sets if certificates presented by the server are going to be checked for their
+- * domain. By default certificates are not verified.
+- *
+- * @param notMatchingDomainCheckEnabled if certificates presented by the server are
going
+- * to be checked for their domain.
+- */
+- public void setNotMatchingDomainCheckEnabled(boolean notMatchingDomainCheckEnabled)
{
+- this.notMatchingDomainCheckEnabled = notMatchingDomainCheckEnabled;
+- }
+-
+ /**
+ * Set the HostnameVerifier used to verify the hostname of SSLSockets used by XMPP
connections
+ * created with this ConnectionConfiguration.
+diff -Nru smack_src_3_2_2/source/org/jivesoftware/smack/ServerTrustManager.java
smack_src_3_2_2-gil/source/org/jivesoftware/smack/ServerTrustManager.java
+--- smack_src_3_2_2/source/org/jivesoftware/smack/ServerTrustManager.java 2012-02-05
03:02:30.000000000 +0100
++++ smack_src_3_2_2-gil/source/org/jivesoftware/smack/ServerTrustManager.java 1970-01-01
01:00:00.000000000 +0100
+@@ -1,259 +0,0 @@
+-/**
+- * $RCSfile$
+- * $Revision: $
+- * $Date: $
+- *
+- * Copyright 2003-2005 Jive Software.
+- *
+- * All rights reserved. Licensed under the Apache License, Version 2.0 (the
"License");
+- * you may not use this file except in compliance with the License.
+- * You may obtain a copy of the License at
+- *
+- *
http://www.apache.org/licenses/LICENSE-2.0
+- *
+- * Unless required by applicable law or agreed to in writing, software
+- * distributed under the License is distributed on an "AS IS" BASIS,
+- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+- * See the License for the specific language governing permissions and
+- * limitations under the License.
+- */
+-
+-package org.jivesoftware.smack;
+-
+-import javax.net.ssl.X509TrustManager;
+-import java.io.FileInputStream;
+-import java.io.InputStream;
+-import java.io.IOException;
+-import java.security.*;
+-import java.security.cert.CertificateException;
+-import java.security.cert.CertificateParsingException;
+-import java.security.cert.X509Certificate;
+-import java.util.*;
+-import java.util.regex.Matcher;
+-import java.util.regex.Pattern;
+-
+-/**
+- * Trust manager that checks all certificates presented by the server. This class
+- * is used during TLS negotiation. It is possible to disable/enable some or all
checkings
+- * by configuring the {@link ConnectionConfiguration}. The truststore file that
contains
+- * knows and trusted CA root certificates can also be configure in {@link
ConnectionConfiguration}.
+- *
+- * @author Gaston Dombiak
+- */
+-class ServerTrustManager implements X509TrustManager {
+-
+- private static Pattern cnPattern = Pattern.compile("(?i)(cn=)([^,]*)");
+-
+- private ConnectionConfiguration configuration;
+-
+- /**
+- * Holds the domain of the remote server we are trying to connect
+- */
+- private String server;
+- private KeyStore trustStore;
+-
+- public ServerTrustManager(String server, ConnectionConfiguration configuration) {
+- this.configuration = configuration;
+- this.server = server;
+-
+- InputStream in = null;
+- try {
+- trustStore = KeyStore.getInstance(configuration.getTruststoreType());
+- in = new FileInputStream(configuration.getTruststorePath());
+- trustStore.load(in, configuration.getTruststorePassword().toCharArray());
+- }
+- catch (Exception e) {
+- e.printStackTrace();
+- // Disable root CA checking
+- configuration.setVerifyRootCAEnabled(false);
+- }
+- finally {
+- if (in != null) {
+- try {
+- in.close();
+- }
+- catch (IOException ioe) {
+- // Ignore.
+- }
+- }
+- }
+- }
+-
+- public X509Certificate[] getAcceptedIssuers() {
+- return new X509Certificate[0];
+- }
+-
+- public void checkClientTrusted(X509Certificate[] arg0, String arg1)
+- throws CertificateException {
+- }
+-
+- public void checkServerTrusted(X509Certificate[] x509Certificates, String arg1)
+- throws CertificateException {
+-
+- int nSize = x509Certificates.length;
+-
+- List<String> peerIdentities = getPeerIdentity(x509Certificates[0]);
+-
+- if (configuration.isVerifyChainEnabled()) {
+- // Working down the chain, for every certificate in the chain,
+- // verify that the subject of the certificate is the issuer of the
+- // next certificate in the chain.
+- Principal principalLast = null;
+- for (int i = nSize -1; i >= 0 ; i--) {
+- X509Certificate x509certificate = x509Certificates[i];
+- Principal principalIssuer = x509certificate.getIssuerDN();
+- Principal principalSubject = x509certificate.getSubjectDN();
+- if (principalLast != null) {
+- if (principalIssuer.equals(principalLast)) {
+- try {
+- PublicKey publickey =
+- x509Certificates[i + 1].getPublicKey();
+- x509Certificates[i].verify(publickey);
+- }
+- catch (GeneralSecurityException generalsecurityexception) {
+- throw new CertificateException(
+- "signature verification failed of " +
peerIdentities);
+- }
+- }
+- else {
+- throw new CertificateException(
+- "subject/issuer verification failed of " +
peerIdentities);
+- }
+- }
+- principalLast = principalSubject;
+- }
+- }
+-
+- if (configuration.isVerifyRootCAEnabled()) {
+- // Verify that the the last certificate in the chain was issued
+- // by a third-party that the client trusts.
+- boolean trusted = false;
+- try {
+- trusted = trustStore.getCertificateAlias(x509Certificates[nSize - 1]) !=
null;
+- if (!trusted && nSize == 1 &&
configuration.isSelfSignedCertificateEnabled())
+- {
+- System.out.println("Accepting self-signed certificate of remote
server: " +
+- peerIdentities);
+- trusted = true;
+- }
+- }
+- catch (KeyStoreException e) {
+- e.printStackTrace();
+- }
+- if (!trusted) {
+- throw new CertificateException("root certificate not trusted of
" + peerIdentities);
+- }
+- }
+-
+- if (configuration.isNotMatchingDomainCheckEnabled()) {
+- // Verify that the first certificate in the chain corresponds to
+- // the server we desire to authenticate.
+- // Check if the certificate uses a wildcard indicating that subdomains are
valid
+- if (peerIdentities.size() == 1 &&
peerIdentities.get(0).startsWith("*.")) {
+- // Remove the wildcard
+- String peerIdentity = peerIdentities.get(0).replace("*.",
"");
+- // Check if the requested subdomain matches the certified domain
+- if (!server.endsWith(peerIdentity)) {
+- throw new CertificateException("target verification failed of
" + peerIdentities);
+- }
+- }
+- else if (!peerIdentities.contains(server)) {
+- throw new CertificateException("target verification failed of
" + peerIdentities);
+- }
+- }
+-
+- if (configuration.isExpiredCertificatesCheckEnabled()) {
+- // For every certificate in the chain, verify that the certificate
+- // is valid at the current time.
+- Date date = new Date();
+- for (int i = 0; i < nSize; i++) {
+- try {
+- x509Certificates[i].checkValidity(date);
+- }
+- catch (GeneralSecurityException generalsecurityexception) {
+- throw new CertificateException("invalid date of " +
server);
+- }
+- }
+- }
+-
+- }
+-
+- /**
+- * Returns the identity of the remote server as defined in the specified
certificate. The
+- * identity is defined in the subjectDN of the certificate and it can also be
defined in
+- * the subjectAltName extension of type "xmpp". When the extension is
being used then the
+- * identity defined in the extension in going to be returned. Otherwise, the value
stored in
+- * the subjectDN is returned.
+- *
+- * @param x509Certificate the certificate the holds the identity of the remote
server.
+- * @return the identity of the remote server as defined in the specified
certificate.
+- */
+- public static List<String> getPeerIdentity(X509Certificate x509Certificate) {
+- // Look the identity in the subjectAltName extension if available
+- List<String> names = getSubjectAlternativeNames(x509Certificate);
+- if (names.isEmpty()) {
+- String name = x509Certificate.getSubjectDN().getName();
+- Matcher matcher = cnPattern.matcher(name);
+- if (matcher.find()) {
+- name = matcher.group(2);
+- }
+- // Create an array with the unique identity
+- names = new ArrayList<String>();
+- names.add(name);
+- }
+- return names;
+- }
+-
+- /**
+- * Returns the JID representation of an XMPP entity contained as a SubjectAltName
extension
+- * in the certificate. If none was found then return <tt>null</tt>.
+- *
+- * @param certificate the certificate presented by the remote entity.
+- * @return the JID representation of an XMPP entity contained as a SubjectAltName
extension
+- * in the certificate. If none was found then return
<tt>null</tt>.
+- */
+- private static List<String> getSubjectAlternativeNames(X509Certificate
certificate) {
+- List<String> identities = new ArrayList<String>();
+- try {
+- Collection<List<?>> altNames =
certificate.getSubjectAlternativeNames();
+- // Check that the certificate includes the SubjectAltName extension
+- if (altNames == null) {
+- return Collections.emptyList();
+- }
+- // Use the type OtherName to search for the certified server name
+- /*for (List item : altNames) {
+- Integer type = (Integer) item.get(0);
+- if (type == 0) {
+- // Type OtherName found so return the associated value
+- try {
+- // Value is encoded using ASN.1 so decode it to get the
server's identity
+- ASN1InputStream decoder = new ASN1InputStream((byte[])
item.toArray()[1]);
+- DEREncodable encoded = decoder.readObject();
+- encoded = ((DERSequence) encoded).getObjectAt(1);
+- encoded = ((DERTaggedObject) encoded).getObject();
+- encoded = ((DERTaggedObject) encoded).getObject();
+- String identity = ((DERUTF8String) encoded).getString();
+- // Add the decoded server name to the list of identities
+- identities.add(identity);
+- }
+- catch (UnsupportedEncodingException e) {
+- // Ignore
+- }
+- catch (IOException e) {
+- // Ignore
+- }
+- catch (Exception e) {
+- e.printStackTrace();
+- }
+- }
+- // Other types are not good for XMPP so ignore them
+- System.out.println("SubjectAltName of invalid type found: " +
certificate);
+- }*/
+- }
+- catch (CertificateParsingException e) {
+- e.printStackTrace();
+- }
+- return identities;
+- }
+-
+-}
+diff -Nru smack_src_3_2_2/source/org/jivesoftware/smack/XMPPConnection.java
smack_src_3_2_2-gil/source/org/jivesoftware/smack/XMPPConnection.java
+--- smack_src_3_2_2/source/org/jivesoftware/smack/XMPPConnection.java 2014-08-21
13:26:03.381514135 +0200
++++ smack_src_3_2_2-gil/source/org/jivesoftware/smack/XMPPConnection.java 2014-08-21
13:18:32.329908422 +0200
+@@ -792,9 +792,9 @@
+ }
+
+ // Verify certificate presented by the server
+- context.init(kms,
+- new javax.net.ssl.TrustManager[]{new
ServerTrustManager(getServiceName(), config)},
+- new java.security.SecureRandom());
++ if (context == null) {
++ context.init(kms, null, new java.security.SecureRandom());
++ }
+ Socket plain = socket;
+ // Secure the plain connection
+ socket = context.getSocketFactory().createSocket(plain,
diff --git a/smack.spec b/smack.spec
index ec4118e..4b4dba0 100644
--- a/smack.spec
+++ b/smack.spec
@@ -1,7 +1,7 @@
%global pkg_version %(echo %version | tr . _)
Name: smack
Version: 3.2.2
-Release: 7%{?dist}
+Release: 8%{?dist}
Summary: Open Source XMPP (Jabber) client library
License: ASL 2.0
URL:
http://www.igniterealtime.org/projects/smack/index.jsp
@@ -17,26 +17,16 @@ Source3: %{name}x-debug-%{version}.pom
# unavailable test resources
# wget -O smack-3.2.2-test-config-test-case.xml
http://svn.igniterealtime.org/svn/repos/smack/tags/smack_3_2_2/test/confi...
Source4: %{name}-%{version}-test-config-test-case.xml
-
# use system libraries
# disable jzlib and xpp3 repackage
-
# disable smack jingle extension. cause: unavailable deps
-
-# jingle/extension/build/lib/Speex.jar mil.jfcom.cie.media ?
-# jingle/extension/build/lib/jmf.jar replace with fmj
-# jingle/extension/build/lib/commons-logging-1.1.jar
-# jingle/extension/build/lib/commons-logging-adapters-1.1.jar
-# jingle/extension/build/lib/commons-logging-api-1.1.jar
-# jingle/extension/build/lib/jspeex-0.9.7-jfcom.jar org.xiph.speex
-# jingle/extension/build/merge/jstun.jar
-# jingle/extension/build/lib/junit.jar
-
# remove classpath from manifest files
# fix javadoc link
# fix build/javadoc/tests classpath
Patch0: %{name}-%{version}-build.patch
+
Patch1: %{name}-3.2.2-CVE-2014-5075.patch
+Patch2: %{name}-3.2.2-CVE-2014-0363.patch
BuildRequires: java-javadoc
BuildRequires: javapackages-local
@@ -85,13 +75,12 @@ rm -rf javadoc/* documentation/*
sed -i.ant-contrib
"s|%{_javadir}/ant/ant-contrib.jar|%{_javadir}/ant-contrib/ant-contrib.jar|"
build/build.xml
%endif
%patch1 -p1
+%patch2 -p1
mkdir -p test/config
cp -p %{SOURCE4} test/config/test-case.xml
# tests problem:
-# [junit] XMPPError connecting to localhost:5222.: remote-server-error(502)
-# XMPPError connecting to localhost:5222.
-# [junit] -- caused by: java.net.ConnectException: Connection refused
+# caused by: java.net.ConnectException: Connection refused
# remove this file unavailable class, in this release isn't available. error: cannot
find symbol
# [javac] import org.jivesoftware.smackx.bytestreams.socks5.Socks5PacketUtils;
rm -r test/org/jivesoftware/smackx/bytestreams/socks5/Socks5ByteStreamTest.java
@@ -107,7 +96,7 @@ rm -r test/org/jivesoftware/smack/ChatTest.java \
test/org/jivesoftware/smack/RosterListenerTest.java \
test/org/jivesoftware/smack/RosterSmackTest.java \
test/org/jivesoftware/smack/RosterInitializedBeforeConnectTest.java \
- test/org/jivesoftware/smack/packet/PrivacyTest.java \
+ test/org/jivesoftware/smack/packet/PrivacyTest.java
%build
@@ -128,6 +117,10 @@ rm -r test/org/jivesoftware/smack/ChatTest.java \
%doc README.html
%changelog
+* Thu Dec 04 2014 gil cattaneo <puntogil(a)libero.it> 3.2.2-8
+- fix for CVE-2014-0363 (rhbz#1093274)
+- remove jzlib systemPath in smackx pom
+
* Thu Aug 21 2014 gil cattaneo <puntogil(a)libero.it> 3.2.2-7
- fix for CVE-2014-5075 (rhbz#1127277)
diff --git a/smackx-3.2.2.pom b/smackx-3.2.2.pom
index 70f86b2..55e02d5 100644
--- a/smackx-3.2.2.pom
+++ b/smackx-3.2.2.pom
@@ -43,8 +43,6 @@
<groupId>com.jcraft</groupId>
<artifactId>jzlib</artifactId>
<version>1.0.7</version>
- <scope>system</scope>
- <systemPath>/usr/share/java/jzlib.jar</systemPath>
</dependency>
<dependency>
<groupId>org.igniterealtime.smack</groupId>