list_ports.py 3.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108
  1. #!/usr/bin/env python
  2. #
  3. # Serial port enumeration. Console tool and backend selection.
  4. #
  5. # This file is part of pySerial. https://github.com/pyserial/pyserial
  6. # (C) 2011-2015 Chris Liechti <cliechti@gmx.net>
  7. #
  8. # SPDX-License-Identifier: BSD-3-Clause
  9. """\
  10. This module will provide a function called comports that returns an
  11. iterable (generator or list) that will enumerate available com ports. Note that
  12. on some systems non-existent ports may be listed.
  13. Additionally a grep function is supplied that can be used to search for ports
  14. based on their descriptions or hardware ID.
  15. """
  16. import sys
  17. import os
  18. import re
  19. # chose an implementation, depending on os
  20. #~ if sys.platform == 'cli':
  21. #~ else:
  22. if os.name == 'nt': # sys.platform == 'win32':
  23. from serial.tools.list_ports_windows import comports
  24. elif os.name == 'posix':
  25. from serial.tools.list_ports_posix import comports
  26. #~ elif os.name == 'java':
  27. else:
  28. raise ImportError("Sorry: no implementation for your platform ('{}') available".format(os.name))
  29. # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  30. def grep(regexp, include_links=False):
  31. """\
  32. Search for ports using a regular expression. Port name, description and
  33. hardware ID are searched. The function returns an iterable that returns the
  34. same tuples as comport() would do.
  35. """
  36. r = re.compile(regexp, re.I)
  37. for info in comports(include_links):
  38. port, desc, hwid = info
  39. if r.search(port) or r.search(desc) or r.search(hwid):
  40. yield info
  41. # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  42. def main():
  43. import argparse
  44. parser = argparse.ArgumentParser(description='Serial port enumeration')
  45. parser.add_argument(
  46. 'regexp',
  47. nargs='?',
  48. help='only show ports that match this regex')
  49. parser.add_argument(
  50. '-v', '--verbose',
  51. action='store_true',
  52. help='show more messages')
  53. parser.add_argument(
  54. '-q', '--quiet',
  55. action='store_true',
  56. help='suppress all messages')
  57. parser.add_argument(
  58. '-n',
  59. type=int,
  60. help='only output the N-th entry')
  61. parser.add_argument(
  62. '-s', '--include-links',
  63. action='store_true',
  64. help='include entries that are symlinks to real devices')
  65. args = parser.parse_args()
  66. hits = 0
  67. # get iteraror w/ or w/o filter
  68. if args.regexp:
  69. if not args.quiet:
  70. sys.stderr.write("Filtered list with regexp: {!r}\n".format(args.regexp))
  71. iterator = sorted(grep(args.regexp, include_links=args.include_links))
  72. else:
  73. iterator = sorted(comports(include_links=args.include_links))
  74. # list them
  75. for n, (port, desc, hwid) in enumerate(iterator, 1):
  76. if args.n is None or args.n == n:
  77. sys.stdout.write("{:20}\n".format(port))
  78. if args.verbose:
  79. sys.stdout.write(" desc: {}\n".format(desc))
  80. sys.stdout.write(" hwid: {}\n".format(hwid))
  81. hits += 1
  82. if not args.quiet:
  83. if hits:
  84. sys.stderr.write("{} ports found\n".format(hits))
  85. else:
  86. sys.stderr.write("no ports found\n")
  87. # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  88. # test
  89. if __name__ == '__main__':
  90. main()