1# 2# This file is part of pyasn1 software. 3# 4# Copyright (c) 2005-2017, Ilya Etingof <etingof@gmail.com> 5# License: http://pyasn1.sf.net/license.html 6# 7import sys 8from pyasn1.type import univ, tag 9from pyasn1 import error 10 11 12__all__ = ['NumericString', 'PrintableString', 'TeletexString', 'T61String', 'VideotexString', 13 'IA5String', 'GraphicString', 'VisibleString', 'ISO646String', 14 'GeneralString', 'UniversalString', 'BMPString', 'UTF8String'] 15 16NoValue = univ.NoValue 17noValue = univ.noValue 18 19 20class AbstractCharacterString(univ.OctetString): 21 """Creates |ASN.1| type or object. 22 23 |ASN.1| objects are immutable and duck-type Python 2 :class:`unicode` or Python 3 :class:`str`. 24 When used in octet-stream context, |ASN.1| type assumes "|encoding|" encoding. 25 26 Parameters 27 ---------- 28 value: :class:`unicode`, :class:`str`, :class:`bytes` or |ASN.1| object 29 unicode object (Python 2) or string (Python 3), alternatively string 30 (Python 2) or bytes (Python 3) representing octet-stream of serialized 31 unicode string (note `encoding` parameter) or |ASN.1| class instance. 32 33 tagSet: :py:class:`~pyasn1.type.tag.TagSet` 34 Object representing non-default ASN.1 tag(s) 35 36 subtypeSpec: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection` 37 Object representing non-default ASN.1 subtype constraint(s) 38 39 encoding: :py:class:`str` 40 Unicode codec ID to encode/decode :class:`unicode` (Python 2) or 41 :class:`str` (Python 3) the payload when |ASN.1| object is used 42 in octet-stream context. 43 44 Raises 45 ------ 46 : :py:class:`pyasn1.error.PyAsn1Error` 47 On constraint violation or bad initializer. 48 """ 49 50 if sys.version_info[0] <= 2: 51 def __str__(self): 52 try: 53 return self._value.encode(self.encoding) 54 except UnicodeEncodeError: 55 raise error.PyAsn1Error( 56 "Can't encode string '%s' with codec %s" % (self._value, self.encoding) 57 ) 58 59 def __unicode__(self): 60 return unicode(self._value) 61 62 def prettyIn(self, value): 63 try: 64 if isinstance(value, unicode): 65 return value 66 elif isinstance(value, str): 67 return value.decode(self.encoding) 68 elif isinstance(value, (tuple, list)): 69 return self.prettyIn(''.join([chr(x) for x in value])) 70 elif isinstance(value, univ.OctetString): 71 return value.asOctets().decode(self.encoding) 72 else: 73 return unicode(value) 74 75 except (UnicodeDecodeError, LookupError): 76 raise error.PyAsn1Error( 77 "Can't decode string '%s' with codec %s" % (value, self.encoding) 78 ) 79 80 def asOctets(self, padding=True): 81 return str(self) 82 83 def asNumbers(self, padding=True): 84 return tuple([ord(x) for x in str(self)]) 85 86 else: 87 def __str__(self): 88 return str(self._value) 89 90 def __bytes__(self): 91 try: 92 return self._value.encode(self.encoding) 93 except UnicodeEncodeError: 94 raise error.PyAsn1Error( 95 "Can't encode string '%s' with codec %s" % (self._value, self.encoding) 96 ) 97 98 def prettyIn(self, value): 99 try: 100 if isinstance(value, str): 101 return value 102 elif isinstance(value, bytes): 103 return value.decode(self.encoding) 104 elif isinstance(value, (tuple, list)): 105 return self.prettyIn(bytes(value)) 106 elif isinstance(value, univ.OctetString): 107 return value.asOctets().decode(self.encoding) 108 else: 109 return str(value) 110 111 except (UnicodeDecodeError, LookupError): 112 raise error.PyAsn1Error( 113 "Can't decode string '%s' with codec %s" % (value, self.encoding) 114 ) 115 116 def asOctets(self, padding=True): 117 return bytes(self) 118 119 def asNumbers(self, padding=True): 120 return tuple(bytes(self)) 121 122 def prettyOut(self, value): 123 return value 124 125 def __reversed__(self): 126 return reversed(self._value) 127 128 def clone(self, value=noValue, **kwargs): 129 """Creates a copy of a |ASN.1| type or object. 130 131 Any parameters to the *clone()* method will replace corresponding 132 properties of the |ASN.1| object. 133 134 Parameters 135 ---------- 136 value: :class:`unicode`, :class:`str`, :class:`bytes` or |ASN.1| object 137 unicode object (Python 2) or string (Python 3), alternatively string 138 (Python 2) or bytes (Python 3) representing octet-stream of serialized 139 unicode string (note `encoding` parameter) or |ASN.1| class instance. 140 141 tagSet: :py:class:`~pyasn1.type.tag.TagSet` 142 Object representing non-default ASN.1 tag(s) 143 144 subtypeSpec: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection` 145 Object representing non-default ASN.1 subtype constraint(s) 146 147 encoding: :py:class:`str` 148 Unicode codec ID to encode/decode :py:class:`unicode` (Python 2) or 149 :py:class:`str` (Python 3) the payload when |ASN.1| object is used 150 in octet-stream context. 151 152 Returns 153 ------- 154 : 155 new instance of |ASN.1| type/value 156 157 """ 158 return univ.OctetString.clone(self, value, **kwargs) 159 160 def subtype(self, value=noValue, **kwargs): 161 """Creates a copy of a |ASN.1| type or object. 162 163 Any parameters to the *subtype()* method will be added to the corresponding 164 properties of the |ASN.1| object. 165 166 Parameters 167 ---------- 168 value: :class:`unicode`, :class:`str`, :class:`bytes` or |ASN.1| object 169 unicode object (Python 2) or string (Python 3), alternatively string 170 (Python 2) or bytes (Python 3) representing octet-stream of serialized 171 unicode string (note `encoding` parameter) or |ASN.1| class instance. 172 173 implicitTag: :py:class:`~pyasn1.type.tag.Tag` 174 Implicitly apply given ASN.1 tag object to caller's 175 :py:class:`~pyasn1.type.tag.TagSet`, then use the result as 176 new object's ASN.1 tag(s). 177 178 explicitTag: :py:class:`~pyasn1.type.tag.Tag` 179 Explicitly apply given ASN.1 tag object to caller's 180 :py:class:`~pyasn1.type.tag.TagSet`, then use the result as 181 new object's ASN.1 tag(s). 182 183 subtypeSpec: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection` 184 Object representing non-default ASN.1 subtype constraint(s) 185 186 encoding: :py:class:`str` 187 Unicode codec ID to encode/decode :py:class:`unicode` (Python 2) or 188 :py:class:`str` (Python 3) the payload when |ASN.1| object is used 189 in octet-stream context. 190 191 Returns 192 ------- 193 : 194 new instance of |ASN.1| type/value 195 196 """ 197 return univ.OctetString.subtype(self, value, **kwargs) 198 199class NumericString(AbstractCharacterString): 200 __doc__ = AbstractCharacterString.__doc__ 201 202 #: Set (on class, not on instance) or return a 203 #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s) 204 #: associated with |ASN.1| type. 205 tagSet = AbstractCharacterString.tagSet.tagImplicitly( 206 tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 18) 207 ) 208 encoding = 'us-ascii' 209 210 # Optimization for faster codec lookup 211 typeId = AbstractCharacterString.getTypeId() 212 213 214class PrintableString(AbstractCharacterString): 215 __doc__ = AbstractCharacterString.__doc__ 216 217 #: Set (on class, not on instance) or return a 218 #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s) 219 #: associated with |ASN.1| type. 220 tagSet = AbstractCharacterString.tagSet.tagImplicitly( 221 tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 19) 222 ) 223 encoding = 'us-ascii' 224 225 # Optimization for faster codec lookup 226 typeId = AbstractCharacterString.getTypeId() 227 228 229class TeletexString(AbstractCharacterString): 230 __doc__ = AbstractCharacterString.__doc__ 231 232 #: Set (on class, not on instance) or return a 233 #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s) 234 #: associated with |ASN.1| type. 235 tagSet = AbstractCharacterString.tagSet.tagImplicitly( 236 tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 20) 237 ) 238 encoding = 'iso-8859-1' 239 240 # Optimization for faster codec lookup 241 typeId = AbstractCharacterString.getTypeId() 242 243 244class T61String(TeletexString): 245 __doc__ = TeletexString.__doc__ 246 247 # Optimization for faster codec lookup 248 typeId = AbstractCharacterString.getTypeId() 249 250 251class VideotexString(AbstractCharacterString): 252 __doc__ = AbstractCharacterString.__doc__ 253 254 #: Set (on class, not on instance) or return a 255 #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s) 256 #: associated with |ASN.1| type. 257 tagSet = AbstractCharacterString.tagSet.tagImplicitly( 258 tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 21) 259 ) 260 encoding = 'iso-8859-1' 261 262 # Optimization for faster codec lookup 263 typeId = AbstractCharacterString.getTypeId() 264 265 266class IA5String(AbstractCharacterString): 267 __doc__ = AbstractCharacterString.__doc__ 268 269 #: Set (on class, not on instance) or return a 270 #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s) 271 #: associated with |ASN.1| type. 272 tagSet = AbstractCharacterString.tagSet.tagImplicitly( 273 tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 22) 274 ) 275 encoding = 'us-ascii' 276 277 # Optimization for faster codec lookup 278 typeId = AbstractCharacterString.getTypeId() 279 280 281class GraphicString(AbstractCharacterString): 282 __doc__ = AbstractCharacterString.__doc__ 283 284 #: Set (on class, not on instance) or return a 285 #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s) 286 #: associated with |ASN.1| type. 287 tagSet = AbstractCharacterString.tagSet.tagImplicitly( 288 tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 25) 289 ) 290 encoding = 'iso-8859-1' 291 292 # Optimization for faster codec lookup 293 typeId = AbstractCharacterString.getTypeId() 294 295 296class VisibleString(AbstractCharacterString): 297 __doc__ = AbstractCharacterString.__doc__ 298 299 #: Set (on class, not on instance) or return a 300 #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s) 301 #: associated with |ASN.1| type. 302 tagSet = AbstractCharacterString.tagSet.tagImplicitly( 303 tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 26) 304 ) 305 encoding = 'us-ascii' 306 307 # Optimization for faster codec lookup 308 typeId = AbstractCharacterString.getTypeId() 309 310 311class ISO646String(VisibleString): 312 __doc__ = VisibleString.__doc__ 313 314 # Optimization for faster codec lookup 315 typeId = AbstractCharacterString.getTypeId() 316 317class GeneralString(AbstractCharacterString): 318 __doc__ = AbstractCharacterString.__doc__ 319 320 #: Set (on class, not on instance) or return a 321 #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s) 322 #: associated with |ASN.1| type. 323 tagSet = AbstractCharacterString.tagSet.tagImplicitly( 324 tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 27) 325 ) 326 encoding = 'iso-8859-1' 327 328 # Optimization for faster codec lookup 329 typeId = AbstractCharacterString.getTypeId() 330 331 332class UniversalString(AbstractCharacterString): 333 __doc__ = AbstractCharacterString.__doc__ 334 335 #: Set (on class, not on instance) or return a 336 #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s) 337 #: associated with |ASN.1| type. 338 tagSet = AbstractCharacterString.tagSet.tagImplicitly( 339 tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 28) 340 ) 341 encoding = "utf-32-be" 342 343 # Optimization for faster codec lookup 344 typeId = AbstractCharacterString.getTypeId() 345 346 347class BMPString(AbstractCharacterString): 348 __doc__ = AbstractCharacterString.__doc__ 349 350 #: Set (on class, not on instance) or return a 351 #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s) 352 #: associated with |ASN.1| type. 353 tagSet = AbstractCharacterString.tagSet.tagImplicitly( 354 tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 30) 355 ) 356 encoding = "utf-16-be" 357 358 # Optimization for faster codec lookup 359 typeId = AbstractCharacterString.getTypeId() 360 361 362class UTF8String(AbstractCharacterString): 363 __doc__ = AbstractCharacterString.__doc__ 364 365 #: Set (on class, not on instance) or return a 366 #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s) 367 #: associated with |ASN.1| type. 368 tagSet = AbstractCharacterString.tagSet.tagImplicitly( 369 tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 12) 370 ) 371 encoding = "utf-8" 372 373 # Optimization for faster codec lookup 374 typeId = AbstractCharacterString.getTypeId() 375