Servo is a prototype web browser engine written in the Rust language. It is currently developed on 64-bit macOS, 64-bit Linux, 64-bit Windows, and Android.
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.
 
 
 
 
 
 

110 lines
4.7 KiB

  1. #!/bin/sh
  2. # This Source Code Form is subject to the terms of the Mozilla Public
  3. # License, v. 2.0. If a copy of the MPL was not distributed with this
  4. # file, You can obtain one at https://mozilla.org/MPL/2.0/.
  5. # The beginning of this script is both valid shell and valid python,
  6. # such that the script starts with the shell and is reexecuted with
  7. # the right python.
  8. ''':' && if [ ! -z "$MSYSTEM" ] ; then exec python "$0" "$@" ; else which python2.7 > /dev/null 2> /dev/null && exec python2.7 "$0" "$@" || exec python "$0" "$@" ; fi
  9. '''
  10. from __future__ import print_function, unicode_literals
  11. import os
  12. import sys
  13. # Check for the current python version as some users (especially on archlinux)
  14. # may not have python 2 installed and their /bin/python binary symlinked to
  15. # python 3.
  16. if sys.version_info >= (3, 0) and sys.version_info < (3, 5):
  17. print("mach does not support python 3 (< 3.5), please install python 2 or python 3 (>= 3.5)")
  18. sys.exit(1)
  19. def main(args):
  20. topdir = os.path.abspath(os.path.dirname(sys.argv[0]))
  21. sys.path.insert(0, os.path.join(topdir, "python"))
  22. import mach_bootstrap
  23. if len(sys.argv) > 1 and sys.argv[1] == "bootstrap":
  24. sys.exit(mach_bootstrap.bootstrap_command_only(topdir))
  25. else:
  26. mach = mach_bootstrap.bootstrap(topdir)
  27. sys.exit(mach.run(sys.argv[1:]))
  28. if __name__ == '__main__':
  29. sys.dont_write_bytecode = True
  30. if sys.platform == 'win32' and sys.version_info < (3, 4):
  31. # This is a complete hack to work around the fact that Windows
  32. # multiprocessing needs to import the original module (ie: this
  33. # file), but only works if it has a .py extension.
  34. #
  35. # We do this by a sort of two-level function interposing. The first
  36. # level interposes forking.get_command_line() with our version defined
  37. # in my_get_command_line(). Our version of get_command_line will
  38. # replace the command string with the contents of the fork_interpose()
  39. # function to be used in the subprocess.
  40. #
  41. # The subprocess then gets an interposed imp.find_module(), which we
  42. # hack up to find 'mach' without the .py extension, since we already
  43. # know where it is (it's us!). If we're not looking for 'mach', then
  44. # the original find_module will suffice.
  45. #
  46. # See also: http://bugs.python.org/issue19946
  47. # And: https://bugzilla.mozilla.org/show_bug.cgi?id=914563
  48. # XXX In Python 3.4 the multiprocessing module was re-written and the
  49. # below code is no longer valid. The Python issue19946 also claims to
  50. # be fixed in this version. It's not clear whether this hack is still
  51. # needed in 3.4+ or not, but at least some basic mach commands appear
  52. # to work without it. So skip it in 3.4+ until we determine it's still
  53. # needed.
  54. import inspect
  55. from multiprocessing import forking
  56. global orig_command_line
  57. def fork_interpose():
  58. import imp
  59. import os
  60. import sys
  61. orig_find_module = imp.find_module
  62. def my_find_module(name, dirs):
  63. if name == 'mach':
  64. path = os.path.join(dirs[0], 'mach')
  65. f = open(path)
  66. return (f, path, ('', 'r', imp.PY_SOURCE))
  67. return orig_find_module(name, dirs)
  68. # Don't allow writing bytecode file for mach module.
  69. orig_load_module = imp.load_module
  70. def my_load_module(name, file, path, description):
  71. # multiprocess.forking invokes imp.load_module manually and
  72. # hard-codes the name __parents_main__ as the module name.
  73. if name == '__parents_main__':
  74. old_bytecode = sys.dont_write_bytecode
  75. sys.dont_write_bytecode = True
  76. try:
  77. return orig_load_module(name, file, path, description)
  78. finally:
  79. sys.dont_write_bytecode = old_bytecode
  80. return orig_load_module(name, file, path, description)
  81. imp.find_module = my_find_module
  82. imp.load_module = my_load_module
  83. from multiprocessing.forking import main; main()
  84. def my_get_command_line():
  85. fork_code, lineno = inspect.getsourcelines(fork_interpose)
  86. # Remove the first line (for 'def fork_interpose():') and the three
  87. # levels of indentation (12 spaces).
  88. fork_string = ''.join(x[12:] for x in fork_code[1:])
  89. cmdline = orig_command_line()
  90. cmdline[2] = fork_string
  91. return cmdline
  92. orig_command_line = forking.get_command_line
  93. forking.get_command_line = my_get_command_line
  94. main(sys.argv)