You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

debug.py 3.6KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157
  1. #
  2. # This file is part of pyasn1 software.
  3. #
  4. # Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>
  5. # License: http://snmplabs.com/pyasn1/license.html
  6. #
  7. import logging
  8. import sys
  9. from pyasn1 import __version__
  10. from pyasn1 import error
  11. from pyasn1.compat.octets import octs2ints
  12. __all__ = ['Debug', 'setLogger', 'hexdump']
  13. DEBUG_NONE = 0x0000
  14. DEBUG_ENCODER = 0x0001
  15. DEBUG_DECODER = 0x0002
  16. DEBUG_ALL = 0xffff
  17. FLAG_MAP = {
  18. 'none': DEBUG_NONE,
  19. 'encoder': DEBUG_ENCODER,
  20. 'decoder': DEBUG_DECODER,
  21. 'all': DEBUG_ALL
  22. }
  23. LOGGEE_MAP = {}
  24. class Printer(object):
  25. # noinspection PyShadowingNames
  26. def __init__(self, logger=None, handler=None, formatter=None):
  27. if logger is None:
  28. logger = logging.getLogger('pyasn1')
  29. logger.setLevel(logging.DEBUG)
  30. if handler is None:
  31. handler = logging.StreamHandler()
  32. if formatter is None:
  33. formatter = logging.Formatter('%(asctime)s %(name)s: %(message)s')
  34. handler.setFormatter(formatter)
  35. handler.setLevel(logging.DEBUG)
  36. logger.addHandler(handler)
  37. self.__logger = logger
  38. def __call__(self, msg):
  39. self.__logger.debug(msg)
  40. def __str__(self):
  41. return '<python logging>'
  42. if hasattr(logging, 'NullHandler'):
  43. NullHandler = logging.NullHandler
  44. else:
  45. # Python 2.6 and older
  46. class NullHandler(logging.Handler):
  47. def emit(self, record):
  48. pass
  49. class Debug(object):
  50. defaultPrinter = Printer()
  51. def __init__(self, *flags, **options):
  52. self._flags = DEBUG_NONE
  53. if 'loggerName' in options:
  54. # route our logs to parent logger
  55. self._printer = Printer(
  56. logger=logging.getLogger(options['loggerName']),
  57. handler=NullHandler()
  58. )
  59. elif 'printer' in options:
  60. self._printer = options.get('printer')
  61. else:
  62. self._printer = self.defaultPrinter
  63. self._printer('running pyasn1 %s, debug flags %s' % (__version__, ', '.join(flags)))
  64. for flag in flags:
  65. inverse = flag and flag[0] in ('!', '~')
  66. if inverse:
  67. flag = flag[1:]
  68. try:
  69. if inverse:
  70. self._flags &= ~FLAG_MAP[flag]
  71. else:
  72. self._flags |= FLAG_MAP[flag]
  73. except KeyError:
  74. raise error.PyAsn1Error('bad debug flag %s' % flag)
  75. self._printer("debug category '%s' %s" % (flag, inverse and 'disabled' or 'enabled'))
  76. def __str__(self):
  77. return 'logger %s, flags %x' % (self._printer, self._flags)
  78. def __call__(self, msg):
  79. self._printer(msg)
  80. def __and__(self, flag):
  81. return self._flags & flag
  82. def __rand__(self, flag):
  83. return flag & self._flags
  84. _LOG = DEBUG_NONE
  85. def setLogger(userLogger):
  86. global _LOG
  87. if userLogger:
  88. _LOG = userLogger
  89. else:
  90. _LOG = DEBUG_NONE
  91. # Update registered logging clients
  92. for module, (name, flags) in LOGGEE_MAP.items():
  93. setattr(module, name, _LOG & flags and _LOG or DEBUG_NONE)
  94. def registerLoggee(module, name='LOG', flags=DEBUG_NONE):
  95. LOGGEE_MAP[sys.modules[module]] = name, flags
  96. setLogger(_LOG)
  97. return _LOG
  98. def hexdump(octets):
  99. return ' '.join(
  100. ['%s%.2X' % (n % 16 == 0 and ('\n%.5d: ' % n) or '', x)
  101. for n, x in zip(range(len(octets)), octs2ints(octets))]
  102. )
  103. class Scope(object):
  104. def __init__(self):
  105. self._list = []
  106. def __str__(self): return '.'.join(self._list)
  107. def push(self, token):
  108. self._list.append(token)
  109. def pop(self):
  110. return self._list.pop()
  111. scope = Scope()