PyDERASN: Als ich die ASN.1-Bibliothek mit Slots und Blobs schrieb

ASN.1 ist ein Standard (ISO, ITU-T, GOST) einer Sprache, die strukturierte Informationen sowie Codierungsregeln für diese Informationen beschreibt. Für mich als Programmierer ist dies neben JSON, XML, XDR und anderen nur ein weiteres Format zum Serialisieren und Präsentieren von Daten. Es ist in unserem normalen Leben sehr verbreitet, und viele Menschen stoßen darauf: in Mobilfunk, Telefon, VoIP-Kommunikation (UMTS, LTE, WiMAX, SS7, H.323), in Netzwerkprotokollen (LDAP, SNMP, Kerberos), in allem In Bezug auf Kryptographie (X.509, CMS, PKCS-Standards), Bankkarten und biometrische Pässe und vieles mehr.

Dieser Artikel beschreibt die PyDERASN : Python ASN.1-Bibliothek, die aktiv in Projekten im Zusammenhang mit Kryptographie in Atlas verwendet wird .

Meine eigene

Tatsächlich lohnt es sich nicht, ASN.1 für kryptografische Aufgaben zu empfehlen: ASN.1 und seine Codecs sind komplex. Dies bedeutet, dass der Code nicht einfach ist, sondern immer ein zusätzlicher Angriffsvektor ist. Schauen Sie sich einfach die Liste der Schwachstellen in ASN.1-Bibliotheken an. Bruce Schneier empfiehlt in seiner Kryptografie-Technik die Verwendung dieses Standards aufgrund seiner Komplexität ebenfalls nicht: "Die bekannteste TLV-Codierung ist ASN.1, aber sie ist unglaublich komplex und wir scheuen sie." Leider verfügen wir heute über Public-Key-Infrastrukturen, in denen X.509-Zertifikate , CRL-, OCSP-, TSP-, CMP-, CMC- , CMS- Nachrichten und viele PKCS- Standards aktiv verwendet werden. Daher müssen Sie in der Lage sein, mit ASN.1 zu arbeiten, wenn Sie etwas im Zusammenhang mit Kryptografie tun.

ASN.1 kann auf verschiedene Arten / Codecs codiert werden:

  • BER (Grundlegende Codierungsregeln)
  • CER (Canonical Encoding Rules)
  • DER (Distinguished Encoding Rules)
  • GSER (Generic String Encoding Rules)
  • JER (JSON-Codierungsregeln)
  • LWER (Light Weight Encoding Rules)
  • OER (Octet Encoding Rules)
  • PER (Packed Encoding Rules)
  • SER (Signalisierungsspezifische Codierungsregeln)
  • XER (XML-Codierungsregeln)

und eine Reihe von anderen. Bei kryptografischen Aufgaben in der Praxis werden jedoch zwei verwendet: BER und DER. Selbst in signierten XML-Dokumenten ( XMLDSig , XAdES ) gibt es weiterhin Base64-codierte ASN.1 DER-Objekte, wie im JSON-basierten ACME- Protokoll von Let's Encrypt. Sie können alle diese Codecs und BER / CER / DER-Codierungsprinzipien in Artikeln und Büchern besser verstehen: ASN.1 in einfachen Worten , ASN.1 - Kommunikation zwischen heterogenen Systemen von Olivier Dubuisson , ASN.1 Vollständig von Prof. John Larmouth .

BER ist ein binäres byteorientiertes TLV-Format (z. B. PER, beliebt in der Mobilkommunikation - bitorientiert). Jedes Element wird in Form von: einem Tag ( T ag) codiert, das den Typ des zu codierenden Elements (Ganzzahl, Zeichenfolge, Datum usw.), die Länge (Länge) des Inhalts und den Inhalt selbst (Wert) identifiziert. Mit BER können Sie optional keinen Längenwert angeben, indem Sie einen speziellen Wert für unbestimmte Länge festlegen und mit einer End-Of-Octets-Nachricht enden. Zusätzlich zur Längencodierung weist BER eine große Variabilität bei der Codierungsmethode für Datentypen auf, wie z.

  • INTEGER, OBJECT IDENTIFIER, BIT STRING und die Länge des Elements dürfen nicht normalisiert werden (nicht in minimaler Form codiert).
  • BOOLEAN gilt für alle Inhalte ungleich Null.
  • BIT STRING kann "zusätzliche" Nullbits enthalten;
  • BIT STRING, OCTET STRING und alle abgeleiteten String-Typen, einschließlich Datum / Uhrzeit, können in Teile (Chunk) variabler Länge unterteilt werden, deren Länge während der (De-) Codierung nicht im Voraus bekannt ist.
  • UTCTime / GeneralizedTime kann verschiedene Methoden zum Einstellen des Zeitzonenversatzes und „zusätzlicher“ Null-Sekundenbruchteile haben.
  • DEFAULT SEQUENCE-Werte können codiert sein oder nicht.
  • Benannte Werte der letzten Bits in BIT STRING können optional codiert werden.
  • SEQUENCE (OF) / SET (OF) können eine beliebige Reihenfolge von Elementen haben.

In all diesen Fällen ist es nicht immer möglich, Daten so zu codieren, dass sie mit dem Originalformular identisch sind. Daher wurde eine Teilmenge der Regeln erfunden: DER ist eine strikte Regelung nur einer gültigen Codierungsmethode, die für kryptografische Aufgaben von entscheidender Bedeutung ist, bei denen beispielsweise durch Ändern eines Bits die Signatur oder Prüfsumme ungültig wird. DER hat einen erheblichen Nachteil: Die Längen aller Elemente müssen während der Codierung im Voraus bekannt sein, da dies keine Stream-Serialisierung von Daten ermöglicht. Der CER-Codec ist frei von diesem Nachteil und garantiert ebenfalls eine eindeutige Darstellung der Daten. Leider (oder zum Glück haben wir keine noch komplexeren Decoder?) Wurde es nicht populär. In der Praxis stoßen wir daher auf eine „gemischte“ Verwendung von BER- und DER-codierten Daten. Da sowohl CER als auch DER eine Teilmenge von BER sind, kann jeder BER-Decoder sie verarbeiten.

Probleme mit pyasn1


Bei der Arbeit schreiben wir viele Python-Programme, die sich auf Kryptographie beziehen. Und vor einigen Jahren gab es praktisch keine Auswahl an freien Bibliotheken: Entweder handelt es sich um Bibliotheken auf sehr niedriger Ebene, mit denen Sie beispielsweise eine Ganzzahl und einen Strukturheader einfach codieren / decodieren können, oder es handelt sich um eine pyasn1- Bibliothek. Wir haben mehrere Jahre darauf gelebt und waren zunächst sehr zufrieden, da Sie damit mit ASN.1-Strukturen als übergeordnete Objekte arbeiten können: Mit einem dekodierten X.509-Zertifikatobjekt können Sie beispielsweise über die Wörterbuchschnittstelle auf seine Felder zugreifen: cert ["tbsCertificate"] ["SerialNumber"] zeigt uns die Seriennummer dieses Zertifikats. Ebenso können Sie komplexe Objekte "sammeln", indem Sie mit ihnen wie mit Listen und Wörterbüchern arbeiten und dann einfach die Funktion pyasn1.codec.der.encoder.encode aufrufen und eine serialisierte Darstellung des Dokuments erhalten.

Es wurden jedoch Schwächen, Probleme und Einschränkungen aufgedeckt. Es gab und gibt leider immer noch Fehler in pyasn1: Zum Zeitpunkt des Schreibens ist in pyasn1 einer der Grundtypen, GeneralizedTime, falsch decodiert und codiert.

Aus Platzgründen speichern wir in unseren Projekten häufig nur den Pfad zur Datei, den Versatz und die Länge des Objekts, auf das wir verweisen möchten, in Byte. Beispielsweise befindet sich eine beliebig signierte Datei höchstwahrscheinlich in der CMS SignedData ASN.1-Struktur:

0 [1,3,1018] ContentInfo SEQUENCE 4 [1,1, 9] . contentType: ContentType OBJECT IDENTIFIER 1.2.840.113549.1.7.2 (id_signedData) 19-4 [0,0,1003] . content: [0] EXPLICIT [UNIV 16] ANY 19 [1,3, 999] . . DEFINED BY id_signedData: SignedData SEQUENCE 23 [1,1, 1] . . . version: CMSVersion INTEGER v3 (03) 26 [1,1, 19] . . . digestAlgorithms: DigestAlgorithmIdentifiers SET OF [...] 47 [1,3, 769] . . . encapContentInfo: EncapsulatedContentInfo SEQUENCE 51 [1,1, 8] . . . . eContentType: ContentType OBJECT IDENTIFIER 1.3.6.1.5.5.7.12.2 (id_cct_PKIData) 65-4 [1,3, 751] . . . . eContent: [0] EXPLICIT OCTET STRING 751 bytes OPTIONAL      751  820 [1,2, 199] . . . signerInfos: SignerInfos SET OF 823 [1,2, 196] . . . . 0: SignerInfo SEQUENCE 826 [1,1, 1] . . . . . version: CMSVersion INTEGER v3 (03) 829 [0,0, 22] . . . . . sid: SignerIdentifier CHOICE subjectKeyIdentifier [...] 956 [1,1, 64] . . . . . signature: SignatureValue OCTET STRING 64 bytes . . . . . . C1:B3:88:BA:F8:92:1C:E6:3E:41:9B:E0:D3:E9:AF:D8 . . . . . . 47:4A:8A:9D:94:5D:56:6B:F0:C1:20:38:D2:72:22:12 . . . . . . 9F:76:46:F6:51:5F:9A:8D:BF:D7:A6:9B:FD:C5:DA:D2 . . . . . . F3:6B:00:14:A4:9D:D7:B5:E1:A6:86:44:86:A7:E8:C9 

und wir können die ursprüngliche signierte Datei mit einem Versatz von 65 Bytes und 751 Bytes Länge erhalten. pyasn1 speichert diese Informationen nicht in seinen dekodierten Objekten. Der sogenannte TLVSeeker wurde geschrieben - eine kleine Bibliothek, mit der Sie die Tags und Längen von Objekten dekodieren können, in deren Schnittstelle wir befohlen haben: "Gehe zum nächsten Tag", "Gehe in das Tag" (Gehe in die SEQUENZ des Objekts), "Gehe zum nächsten Tag", "Sag es dir" Versatz und die Länge des Objekts, in dem wir uns befinden. " Es war ein „manueller“ Spaziergang mit ASN.1 DER-serialisierten Daten. Es war jedoch nicht möglich, auf diese Weise mit BER-serialisierten Daten zu arbeiten, da beispielsweise die Byte-Zeichenfolge OCTET STRING als mehrere Chunk-s codiert werden könnte.

Ein weiterer Nachteil unserer pyasn1-Aufgaben ist die Unfähigkeit, anhand dekodierter Objekte zu verstehen, ob ein bestimmtes Feld in SEQUENCE vorhanden war oder nicht. Wenn die Struktur beispielsweise das Feld Feld SEQUENCE OF Smth OPTIONAL enthält, kann es in den empfangenen Daten (OPTIONAL) vollständig fehlen, aber vorhanden sein, aber gleichzeitig die Länge Null haben (leere Liste). Im allgemeinen Fall konnte dies nicht geklärt werden. Und dies ist notwendig für eine strenge Überprüfung der Gültigkeit der empfangenen Daten. Stellen Sie sich vor, eine Zertifizierungsstelle würde ein Zertifikat mit "nicht vollständig" gültigen Daten aus Sicht der ASN.1-Schemata ausstellen! Beispielsweise hat die Zertifizierungsstelle TÜRKTRUST Elektronik Sertifika Hizmet Sağlayıcısı in ihrem Stammzertifikat die zulässigen RFC 5280- Grenzen für die Länge der betreffenden Komponente überschritten - sie kann gemäß dem Schema nicht ehrlich dekodiert werden. Der DER-Codec erfordert, dass ein Feld mit dem Wert DEFAULT während der Übertragung nicht codiert wird - solche Dokumente werden im Leben angetroffen, und die erste Version von PyDERASN hat aus Gründen der Abwärtskompatibilität sogar bewusst ein solches ungültiges (aus Sicht von DER) Verhalten zugelassen.

Eine weitere Einschränkung ist die Unfähigkeit, leicht herauszufinden, in welcher Form (BER / DER) das eine oder andere Objekt in der Struktur codiert wurde. Der CMS-Standard besagt beispielsweise, dass die Nachricht BER-codiert ist, das Feld signiertAttrs, über das die kryptografische Signatur gebildet wird, sollte sich jedoch in DER befinden. Wenn wir mit dem DER dekodieren, fallen wir auf die Verarbeitung des CMS selbst zurück. Wenn wir mit dem BER dekodieren, wissen wir nicht, in welcher Form signierte Attribute waren. Infolgedessen muss TLVSeeker (dessen Analogon nicht in pyasn1 enthalten ist) nach der Position jedes der signiertenAttrs-Felder suchen und sollte von DER separat aus der serialisierten Ansicht dekodiert werden.

Die Möglichkeit der automatischen Verarbeitung von DEFINED BY-Feldern, die sehr häufig sind, war für uns sehr wünschenswert. Nach dem Dekodieren der ASN.1-Struktur sind möglicherweise noch viele Felder übrig, die gemäß dem auf der Grundlage des im Strukturfeld angegebenen OBJECT IDENTIFIER ausgewählten Schemas weiterverarbeitet werden sollten. Im Python-Code bedeutet dies, ein if zu schreiben und dann den Decoder für das ANY-Feld aufzurufen.

Das Aufkommen von PyDERASN


In Atlas senden wir regelmäßig Patches nach oben, nachdem wir Probleme festgestellt oder die verwendeten kostenlosen Programme geändert haben. In pyasn1 haben wir mehrmals Verbesserungen gesendet, aber der pyasn1-Code ist nicht so einfach zu verstehen, und manchmal traten inkompatible API-Änderungen auf, die uns auf die Hände trafen. Außerdem sind wir es gewohnt, Tests mit generativen Tests zu schreiben, was bei pyasn1 nicht der Fall war.

Eines schönen Tages entschied ich, dass ich das ertragen musste und es war Zeit zu versuchen, meine eigene Bibliothek mit __slot __s, Offset s und wunderschön angezeigten Blobs zu schreiben! Nur einen ASN.1-Codec zu erstellen, würde nicht ausreichen - Sie müssen alle unsere abhängigen Projekte darauf übertragen, und dies sind Hunderttausende von Codezeilen, in denen viel mit ASN.1-Strukturen gearbeitet wird. Dies ist eine der Voraussetzungen dafür: einfache Übersetzung des aktuellen pyasn1-Codes. Nachdem ich meinen gesamten Urlaub verbracht hatte, schrieb ich diese Bibliothek und übertrug alle Projekte darauf. Da sie durch Tests zu fast 100% abgedeckt sind, war die Bibliothek auch voll funktionsfähig.

PyDERASN hat ebenfalls eine Testabdeckung von fast 100%. Generative Tests werden mit der wunderbaren Hypothesenbibliothek verwendet. Auch das Fuzzing von Py-Afl auf 32 Nuklearmaschinen wurde durchgeführt. Trotz der Tatsache, dass wir fast keinen Python2-Code mehr haben, bleibt PyDERASN weiterhin kompatibel und hat aus diesem Grund eine einzige Abhängigkeit von sechs . Darüber hinaus wird es anhand der ASN.1: 2008-Konformitätstestsuite getestet .

Das Prinzip der Arbeit damit ähnelt pyasn1 - Arbeiten mit Python-Objekten auf hoher Ebene. Die Beschreibung der ASN.1-Schaltkreise ist ähnlich.

 class TBSCertificate(Sequence): schema = ( ("version", Version(expl=tag_ctxc(0), default="v1")), ("serialNumber", CertificateSerialNumber()), ("signature", AlgorithmIdentifier()), ("issuer", Name()), ("validity", Validity()), ("subject", Name()), ("subjectPublicKeyInfo", SubjectPublicKeyInfo()), ("issuerUniqueID", UniqueIdentifier(impl=tag_ctxp(1), optional=True)), ("subjectUniqueID", UniqueIdentifier(impl=tag_ctxp(2), optional=True)), ("extensions", Extensions(expl=tag_ctxc(3), optional=True)), ) 

PyDERASN hat jedoch den Anschein einer starken Typisierung. Wenn das Feld in pyasn1 vom Typ CMSVersion (INTEGER) war, konnte ihm ein int oder INTEGER zugewiesen werden. PyDERASN setzt unbedingt voraus, dass das zugewiesene Objekt genau CMSVersion ist. Zusätzlich zum Schreiben von Python3-Code verwenden wir Tippanmerkungen, sodass unsere Funktionen keine unverständlichen Argumente wie def func (seriell, Inhalt), sondern def func (seriell: CertificateSerialNumber, Inhalt: EncapsulatedContentInfo) enthalten und PyDERASN dabei hilft, den Überblick zu behalten Code.

Gleichzeitig hat PyDERASN äußerst bequeme Zugeständnisse für diese Typisierung. pyasn1 erlaubte SubjectKeyIdentifier (). subtype (implicitTag = Tag (...)) nicht, ein SubjectKeyIdentifier () -Objekt zuzuweisen (ohne den erforderlichen IMPLICIT-TAG) und musste Objekte häufig nur aufgrund geänderter IMPLICIT / EXPLICIT-Tags kopieren und neu erstellen. PyDERASN beachtet streng nur den Basistyp - es ersetzt automatisch Tags aus einer vorhandenen ASN.1-Struktur. Dies vereinfacht den Anwendungscode erheblich.

Wenn beim Decodieren ein Fehler auftritt, ist es in pyasn1 nicht einfach, genau zu verstehen, wo er aufgetreten ist. Im bereits erwähnten türkischen Zertifikat wird beispielsweise der folgende Fehler angezeigt: UTF8String (tbsCertificate: issuer: rdnSequence: 3: 0: value: DEFINED BY 2.5.4.10:utf8String) (bei 138) Unbefriedigte Grenzen: 1 ⇐ 77 ⇐ 64 Beim Schreiben von ASN .1 Strukturen Menschen können Fehler machen, und es hilft, Anwendungen zu debuggen oder Probleme mit verschlüsselten Dokumenten der Gegenseite herauszufinden.

Die erste Version von PyDERASN unterstützte keine BER-Codierung. Es erschien viel später und die UTCTime / GeneralizedTime-Verarbeitung mit Zeitzonen wird immer noch nicht unterstützt. Dies wird in Zukunft geschehen, da das Projekt hauptsächlich in der Freizeit geschrieben wird.

Auch in der ersten Version gab es keine Arbeit mit DEFINED BY-Feldern. Einige Monate später erschien diese Gelegenheit und wurde aktiv genutzt, wodurch der Anwendungscode erheblich reduziert wurde. In einem Dekodierungsvorgang konnte die gesamte Struktur bis in die Tiefe zerlegt werden. Zu diesem Zweck werden im Schema die Felder definiert, die "bestimmen". Zum Beispiel eine Beschreibung eines CMS-Schemas:

 class ContentInfo(Sequence): schema = ( ("contentType", ContentType(defines=((("content",), { id_authenticatedData: AuthenticatedData(), id_digestedData: DigestedData(), id_encryptedData: EncryptedData(), id_envelopedData: EnvelopedData(), id_signedData: SignedData(), }),))), ("content", Any(expl=tag_ctxc(0))), ) 

besagt, dass, wenn contentType eine OID mit id_signedData enthält, das Inhaltsfeld (in derselben SEQUENCE) mit dem SignedData-Schema dekodiert werden muss. Warum gibt es so viele Klammern? Ein Feld kann mehrere Felder gleichzeitig „definieren“, wie dies bei EnvelopedData-Strukturen der Fall ist. Definierte Felder werden durch den sogenannten Dekodierungspfad identifiziert - er legt die genaue Position eines Elements in allen Strukturen fest.

Es ist nicht immer wünschenswert oder nicht immer möglich, diese Definitionen sofort in die Schaltung einzuführen. Es kann anwendungsspezifische Fälle geben, in denen OIDs und Strukturen nur in einem Drittanbieterprojekt bekannt sind. PyDERASN bietet die Möglichkeit, diese Definitionen direkt zum Zeitpunkt der Dekodierung der Struktur anzugeben:

 ContentInfo().decode(data, ctx={"defines_by_path": (( ( "content", DecodePathDefBy(id_signedData), "certificates", any, "certificate", "tbsCertificate", "extensions", any, "extnID", ), ((("extnValue",), { id_ce_authorityKeyIdentifier: AuthorityKeyIdentifier(), id_ce_basicConstraints: BasicConstraints(), [...] id_ru_subjectSignTool: SubjectSignTool(), }),), ),)}) 

Hier sagen wir, dass Sie in CMS SignedData für alle angehängten Zertifikate alle ihre Erweiterungen (AuthorityKeyIdentifier, BasicConstraints, SubjectSignTool usw.) dekodieren. Wir geben durch den Decodierungspfad an, welches Element "ersetzt" werden soll, als ob es in der Schaltung definiert wäre.

Schließlich hat PyDERASN die Möglichkeit, über die Befehlszeile ASN.1-Dateien zu dekodieren, und verfügt über ein reichhaltiges, hübsches Drucken . Sie können eine beliebige ASN.1 dekodieren oder ein klar definiertes Schema angeben und Folgendes sehen:

Hübsches Druckbeispiel

Angezeigte Informationen: Objektversatz, Tag-Länge, Längenlänge, Inhaltslänge, Vorhandensein von EOC (Ende der Oktette), BER-Codierungsflag, Codierungsflag mit unbestimmter Länge, EXPLICIT-Tag-Länge und Versatz (falls vorhanden), Objektverschachtelungstiefe in Strukturen, IMPLICIT / EXPLICIT-Tag-Wert, Objektname gemäß dem Schema, sein grundlegender ASN.1-Typ, Seriennummer innerhalb von SEQUENCE / SET OF, Wert CHOICE (falls vorhanden), lesbarer Name INTEGER / ENUMERATED / BIT STRING gemäß dem Schema, Wert eines beliebigen Basistyps , DEFAULT / OPTIONAL-Flag von der Schaltung, ein Zeichen dafür, dass das Objekt automatisch als DEFINED BY und danach dekodiert wurde g OID-und es passiert ist, chelovekochitaemy OID.

Das hübsche Drucksystem ist speziell so konstruiert, dass es eine Folge von PP-Objekten erzeugt, die bereits auf separate Weise visualisiert werden. Der Screenshot zeigt den Renderer in einfarbigem Text. Es gibt Renderer im JSON / HTML-Format, so dass dies durch Hervorheben im ASN.1-Browser wie im asn1js- Projekt sichtbar wird .

Andere Bibliotheken


Dies war nicht das Ziel, aber PyDERASN war deutlich schneller als pyasn1. Beispielsweise kann das Dekodieren von CRL-Dateien mit Megabyte-Größe so lange dauern, dass Sie über Zwischenformate zum Speichern von Daten (schnell) nachdenken und die Architektur von Anwendungen ändern müssen. pyasn1 dekodiert CRL CACert.org für mehr als 20 Minuten auf meinem Laptop, während PyDERASN in nur 28 Sekunden! Es gibt ein asn1crypto- Projekt, das darauf abzielt, schnell mit kryptografischen Strukturen zu arbeiten: Es dekodiert (vollständig, nicht träge) dieselbe CRL in 29 Sekunden, verbraucht jedoch fast doppelt so viel RAM, wenn es unter Python3 ausgeführt wird (983 MiB gegenüber 498). und 3,5-mal unter Python2 (1677 gegen 488), während pyasn1 bis zu 4,3-mal mehr verbraucht (2093 gegen 488).

asn1crypto, das ich erwähnte, haben wir nicht berücksichtigt, da das Projekt noch in den Kinderschuhen steckte und wir nichts davon gehört hatten. Jetzt würden sie auch nicht in seine Richtung schauen, da ich sofort herausfand, dass er nicht dieselbe GeneralizedTime akzeptiert, und während der Serialisierung entfernt er stillschweigend Sekundenbruchteile. Dies ist für die Arbeit mit X.509-Zertifikaten akzeptabel, funktioniert jedoch im Allgemeinen nicht.

Im Moment ist PyDERASN der strengste freie Python / Go DER-Decoder, den ich kenne. In der encoding / asn1-Bibliothek meines Lieblings-Go werden die Zeichenfolgen OBJECT IDENTIFIER und UTCTime / GeneralizedTime nicht streng überprüft . Manchmal kann die Strenge stören (vor allem aufgrund der Abwärtskompatibilität mit alten Anwendungen, die niemand beheben wird), sodass Sie in PyDERASN während der Dekodierung verschiedene Schwächungsprüfungen für Einstellungen bestehen können.

Der Projektcode versucht so einfach wie möglich zu sein. Die gesamte Bibliothek ist eine einzelne Datei. Der Code wurde mit Schwerpunkt auf Verständlichkeit geschrieben, ohne unnötige Leistung und DRY-Code-Optimierungen. Wie ich bereits sagte, unterstützt es nicht die vollständige BER-Decodierung von UTCTime / GeneralizedTime-Zeichenfolgen sowie die Datentypen REAL, RELATIVE OID, EXTERNAL, INSTANCE OF, EMBEDDED PDV und CHARACTER STRING. In allen anderen Fällen sehe ich persönlich keinen Grund, andere Bibliotheken in Python zu verwenden.

Wie alle meine Projekte wie PyGOST , GoGOST , NNCP , GoVPN ist PyDERASN eine völlig kostenlose Software, die unter den Bedingungen von LGPLv3 + vertrieben wird und zum kostenlosen Download zur Verfügung steht. Anwendungsbeispiele finden Sie hier in PyGOST-Tests .

Sergey Matveev , Chiffrierbank , Mitglied der Open Society Foundation Foundation , Python / Go-Entwickler, Chefspezialist des FSUE „Scientific and Technical Center“ Atlas “ .

Source: https://habr.com/ru/post/de444272/


All Articles