99from __future__ import unicode_literals
1010
1111import argparse
12+ import os
1213import shutil
1314import socket
1415import subprocess
1516import sys
1617import tempfile
18+ import threading
1719import time
1820
1921from thrift .protocol import TBinaryProtocol
@@ -144,6 +146,19 @@ def parse_cli_params():
144146 help = "Enable verbose informational messages" )
145147 return parser .parse_args ()
146148
149+ def start_watcher (client , interval ):
150+ """Ping the osquery extension manager to detect dirty shutdowns."""
151+ try :
152+ while True :
153+ status = client .extension_manager_client ().ping ()
154+ if status .code is not 0 :
155+ break
156+ time .sleep (interval )
157+ except socket .error :
158+ # The socket was torn down.
159+ pass
160+ os ._exit (0 )
161+
147162def start_extension (name = "<unknown>" , version = "0.0.0" , sdk_version = "1.8.0" ,
148163 min_sdk_version = "1.8.0" ):
149164 """Start your extension by communicating with osquery core and starting
@@ -157,7 +172,8 @@ def start_extension(name="<unknown>", version="0.0.0", sdk_version="1.8.0",
157172 """
158173 args = parse_cli_params ()
159174 client = ExtensionClient (path = args .socket )
160- client .open ()
175+ if not client .open (args .timeout ):
176+ return
161177 ext_manager = ExtensionManager ()
162178
163179 # try connecting to the desired osquery core extension manager socket
@@ -184,6 +200,11 @@ def start_extension(name="<unknown>", version="0.0.0", sdk_version="1.8.0",
184200 message = status .message ,
185201 )
186202
203+ # Start a watchdog thread to monitor the osquery process.
204+ rt = threading .Thread (target = start_watcher , args = (client , args .interval ))
205+ rt .daemon = True
206+ rt .start ()
207+
187208 # start a thrift server listening at the path dictated by the uuid returned
188209 # by the osquery core extension manager
189210 ext_manager .uuid = status .uuid
0 commit comments