parse SAN otherNames into OtherName instances rather than raising an exception

Test added.
diff --git a/docs/x509.rst b/docs/x509.rst
index f94f50e..eab1f53 100644
--- a/docs/x509.rst
+++ b/docs/x509.rst
@@ -695,6 +695,20 @@
 
         :type: :class:`ObjectIdentifier`
 
+.. class:: OtherName
+
+    .. versionadded:: 1.0
+
+    This corresponds to an "otherName."  An otherName has a type identifier and a value represented in binary DER format.
+
+    .. attribute:: type_id
+
+        :type: :class:`ObjectIdentifier`
+
+    .. attribute:: value
+
+        :type: `bytes`
+
 X.509 Extensions
 ~~~~~~~~~~~~~~~~
 
diff --git a/src/_cffi_src/openssl/asn1.py b/src/_cffi_src/openssl/asn1.py
index 5210c7c..01d6f4c 100644
--- a/src/_cffi_src/openssl/asn1.py
+++ b/src/_cffi_src/openssl/asn1.py
@@ -155,6 +155,8 @@
 
 /* Not a macro, const on openssl 1.0 */
 int ASN1_STRING_set_default_mask_asc(char *);
+
+int i2d_ASN1_TYPE(ASN1_TYPE *, unsigned char **);
 """
 
 CUSTOMIZATIONS = """
diff --git a/src/cryptography/hazmat/backends/openssl/x509.py b/src/cryptography/hazmat/backends/openssl/x509.py
index 80e5f2b..e720bfd 100644
--- a/src/cryptography/hazmat/backends/openssl/x509.py
+++ b/src/cryptography/hazmat/backends/openssl/x509.py
@@ -47,6 +47,17 @@
     return backend._ffi.buffer(buf[0], res)[:].decode('utf8')
 
 
+def _asn1_to_der(backend, asn1_type):
+    buf = backend._ffi.new("unsigned char **")
+    res = backend._lib.i2d_ASN1_TYPE(asn1_type, buf)
+    assert res >= 0
+    assert buf[0] != backend._ffi.NULL
+    buf = backend._ffi.gc(
+        buf, lambda buffer: backend._lib.OPENSSL_free(buffer[0])
+    )
+    return backend._ffi.buffer(buf[0], res)[:]
+
+
 def _decode_x509_name_entry(backend, x509_name_entry):
     obj = backend._lib.X509_NAME_ENTRY_get_object(x509_name_entry)
     assert obj != backend._ffi.NULL
@@ -157,8 +168,12 @@
             return x509.RFC822Name(
                 parts[0] + u"@" + idna.decode(parts[1])
             )
+    elif gn.type == backend._lib.GEN_OTHERNAME:
+        type_id = _obj2txt(backend, gn.d.otherName.type_id)
+        value = _asn1_to_der(backend, gn.d.otherName.value)
+        return x509.OtherName(x509.ObjectIdentifier(type_id), value)
     else:
-        # otherName, x400Address or ediPartyName
+        # x400Address or ediPartyName
         raise x509.UnsupportedGeneralNameType(
             "{0} is not a supported type".format(
                 x509._GENERAL_NAMES.get(gn.type, gn.type)
diff --git a/src/cryptography/x509.py b/src/cryptography/x509.py
index afd28f2..48949b6 100644
--- a/src/cryptography/x509.py
+++ b/src/cryptography/x509.py
@@ -1045,6 +1045,34 @@
         return not self == other
 
 
+@utils.register_interface(GeneralName)
+class OtherName(object):
+    def __init__(self, type_id, value):
+        if not isinstance(type_id, ObjectIdentifier):
+            raise TypeError("type_id must be an ObjectIdentifier")
+        if not isinstance(value, bytes):
+            raise TypeError("value must be a binary string")
+
+        self._type_id = type_id
+        self._value = value
+
+    type_id = utils.read_only_property("_type_id")
+    value = utils.read_only_property("_value")
+
+    def __repr__(self):
+        return "<OtherName(type_id={0}, value={1!r})>".format(
+            self.type_id, self.value)
+
+    def __eq__(self, other):
+        if not isinstance(other, OtherName):
+            return NotImplemented
+
+        return self.type_id == other.type_id and self.value == other.value
+
+    def __ne__(self, other):
+        return not self == other
+
+
 class GeneralNames(object):
     def __init__(self, general_names):
         if not all(isinstance(x, GeneralName) for x in general_names):
diff --git a/tests/test_x509_ext.py b/tests/test_x509_ext.py
index d15d666..06adaa3 100644
--- a/tests/test_x509_ext.py
+++ b/tests/test_x509_ext.py
@@ -1578,6 +1578,30 @@
 
         assert 'Invalid rfc822name value' in str(exc.value)
 
+    def test_other_name(self, backend):
+        cert = _load_cert(
+            os.path.join(
+                "x509", "custom", "san_other_name.pem"
+            ),
+            x509.load_pem_x509_certificate,
+            backend
+        )
+
+        ext = cert.extensions.get_extension_for_oid(
+            x509.OID_SUBJECT_ALTERNATIVE_NAME
+        )
+        assert ext is not None
+        assert ext.critical is False
+
+        assert len(ext.value) == 1
+        assert list(ext.value)[0] == \
+            x509.OtherName(
+                x509.ObjectIdentifier("1.2.3.4"),
+                b'\x16\x0bHello World')
+
+        othernames = ext.value.get_values_for_type(x509.OtherName)
+        assert othernames == [b'\x16\x0bHello World']
+
 
 @pytest.mark.requires_backend_interface(interface=RSABackend)
 @pytest.mark.requires_backend_interface(interface=X509Backend)