1#!/usr/bin/env python 2# 3# ===- pipeline_helper.py - Remote Index pipeline Helper *- python -------*--===# 4# 5# Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 6# See https://llvm.org/LICENSE.txt for license information. 7# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 8# 9# ===------------------------------------------------------------------------===# 10 11import argparse 12import os 13import subprocess 14from socket import socket 15import sys 16import time 17import threading 18 19 20def kill_process_after_delay(server_process): 21 time.sleep(10) 22 if server_process.poll() is None: 23 server_process.kill() 24 25 26def main(): 27 parser = argparse.ArgumentParser() 28 parser.add_argument("--input-file-name", required=True) 29 parser.add_argument("--project-root", required=True) 30 parser.add_argument("--index-file", required=True) 31 parser.add_argument("--server-arg", action="append", default=[]) 32 parser.add_argument( 33 "--server-log", nargs="?", type=argparse.FileType("wb"), default=os.devnull 34 ) 35 36 args = parser.parse_args() 37 38 # Grab an available port. 39 with socket() as s: 40 s.bind(("localhost", 0)) 41 server_address = "localhost:" + str(s.getsockname()[1]) 42 43 print("Initializing clangd-index-server...", file=sys.stderr) 44 index_server_process = subprocess.Popen( 45 [ 46 "clangd-index-server", 47 "--server-address=" + server_address, 48 args.index_file, 49 args.project_root, 50 ] 51 + args.server_arg, 52 stderr=subprocess.PIPE, 53 ) 54 55 # This will kill index_server_process if it hangs without printing init 56 # message. 57 shutdown_thread = threading.Thread( 58 target=kill_process_after_delay, args=(index_server_process,) 59 ) 60 shutdown_thread.daemon = True 61 shutdown_thread.start() 62 63 # Wait for the server to warm-up. 64 found_init_message = False 65 while index_server_process.poll() is None: 66 line = index_server_process.stderr.readline() 67 args.server_log.write(line) 68 args.server_log.flush() 69 if b"Server listening" in line: 70 print("Server initialization complete.", file=sys.stderr) 71 found_init_message = True 72 break 73 74 if not found_init_message: 75 print("Server initialization failed. Shutting down.", file=sys.stderr) 76 sys.exit(1) 77 78 print("Running clangd-index-server-monitor...", file=sys.stderr) 79 index_server_monitor_process = subprocess.Popen( 80 [ 81 "clangd-index-server-monitor", 82 server_address, 83 ], 84 stderr=subprocess.PIPE, 85 ) 86 87 index_server_monitor_process.wait() 88 89 in_file = open(args.input_file_name) 90 91 print("Staring clangd...", file=sys.stderr) 92 clangd_process = subprocess.Popen( 93 [ 94 "clangd", 95 "--remote-index-address=" + server_address, 96 "--project-root=" + args.project_root, 97 "--lit-test", 98 "--sync", 99 ], 100 stdin=in_file, 101 ) 102 clangd_process.wait() 103 print( 104 "Clangd executed successfully, shutting down child processes.", file=sys.stderr 105 ) 106 index_server_process.kill() 107 for line in index_server_process.stderr: 108 args.server_log.write(line) 109 args.server_log.flush() 110 111 for line in index_server_monitor_process.stderr: 112 args.server_log.write(line) 113 args.server_log.flush() 114 115 116if __name__ == "__main__": 117 main() 118