def emulate(n_lpu, n_spike, n_gpot, steps): """ Benchmark inter-LPU communication throughput. Each LPU is configured to use a different local GPU. Parameters ---------- n_lpu : int Number of LPUs. Must be at least 2 and no greater than the number of local GPUs. n_spike : int Total number of input and output spiking ports any single LPU exposes to any other LPU. Each LPU will therefore have 2*n_spike*(n_lpu-1) total spiking ports. n_gpot : int Total number of input and output graded potential ports any single LPU exposes to any other LPU. Each LPU will therefore have 2*n_gpot*(n_lpu-1) total graded potential ports. steps : int Number of steps to execute. Returns ------- average_throughput, total_throughput : float Average per-step and total received data throughput in bytes/seconds. exec_time : float Execution time in seconds. """ # Time everything starting with manager initialization: start_all = time.time() # Check whether a sufficient number of GPUs are available: drv.init() if n_lpu > drv.Device.count(): raise RuntimeError('insufficient number of available GPUs.') # Set up manager and broker: man = Manager(get_random_port(), get_random_port(), get_random_port()) man.add_brok() # Generate selectors for configuring modules and patterns: mod_sels, pat_sels = gen_sels(n_lpu, n_spike, n_gpot) # Set up modules: for i in xrange(n_lpu): lpu_i = 'lpu%s' % i sel, sel_in, sel_out, sel_gpot, sel_spike = mod_sels[lpu_i] m = MyModule(sel, sel_in, sel_out, sel_gpot, sel_spike, port_data=man.port_data, port_ctrl=man.port_ctrl, port_time=man.port_time, id=lpu_i, device=i, debug=args.debug) man.add_mod(m) # Set up connections between module pairs: for i, j in itertools.combinations(xrange(n_lpu), 2): lpu_i = 'lpu%s' % i lpu_j = 'lpu%s' % j sel_from, sel_to, sel_in_i, sel_out_i, sel_gpot_i, sel_spike_i, \ sel_in_j, sel_out_j, sel_gpot_j, sel_spike_j = pat_sels[(lpu_i, lpu_j)] pat = Pattern.from_concat(sel_from, sel_to, from_sel=sel_from, to_sel=sel_to, data=1) pat.interface[sel_in_i, 'interface', 'io'] = [0, 'in'] pat.interface[sel_out_i, 'interface', 'io'] = [0, 'out'] pat.interface[sel_gpot_i, 'interface', 'type'] = [0, 'gpot'] pat.interface[sel_spike_i, 'interface', 'type'] = [0, 'spike'] pat.interface[sel_in_j, 'interface', 'io'] = [1, 'in'] pat.interface[sel_out_j, 'interface', 'io'] = [1, 'out'] pat.interface[sel_gpot_j, 'interface', 'type'] = [1, 'gpot'] pat.interface[sel_spike_j, 'interface', 'type'] = [1, 'spike'] man.connect(man.modules[lpu_i], man.modules[lpu_j], pat, 0, 1, compat_check=False) start_main = time.time() man.start(steps=steps) man.stop() stop_main = time.time() t = man.get_throughput() return t[0], (time.time()-start_all), (stop_main-start_main), t[3]
conn = Connectivity(N_gpot_0, N_spike_0, N_gpot_1, N_spike_1, 1, lpu_dict[lpu_0]['id'], lpu_dict[lpu_1]['id'], syn_params) # Define synapses between spiking neurons in both directions: for id_src, id_dest, N_spike_src, N_spike_dest in \ [(lpu_dict[lpu_0]['id'], lpu_dict[lpu_1]['id'], N_spike_0, N_spike_1), (lpu_dict[lpu_1]['id'], lpu_dict[lpu_0]['id'], N_spike_1, N_spike_0)]: id_start = 0 for id, (i, j) in enumerate(itertools.product(xrange(N_spike_src), xrange(N_spike_dest)), id_start): conn[id_src, 'spike', i, id_dest, 'spike', j] = 1 conn[id_src, 'spike', i, id_dest, 'spike', j, 0, 'name'] = \ 'syn_%s:%s_%s:%s' % (id_src, i, id_dest, j) conn[id_src, 'spike', i, id_dest, 'spike', j, 0, 'model'] = 'AlphaSynapse' conn[id_src, 'spike', i, id_dest, 'spike', j, 0, 'ad'] = 0.19*1000 conn[id_src, 'spike', i, id_dest, 'spike', j, 0, 'ar'] = 1.1*100 conn[id_src, 'spike', i, id_dest, 'spike', j, 0, 'class'] = 0 # spike->spike conn[id_src, 'spike', i, id_dest, 'spike', j, 0, 'conductance'] = True conn[id_src, 'spike', i, id_dest, 'spike', j, 0, 'gmax'] = 0.003 conn[id_src, 'spike', i, id_dest, 'spike', j, 0, 'id'] = id conn[id_src, 'spike', i, id_dest, 'spike', j, 0, 'reverse'] = 0.065 id_start = id+1 man.connect(lpu_dict[lpu_0]['lpu'], lpu_dict[lpu_1]['lpu'], conn) man.start(steps=steps) man.stop()
def emulate(n_lpu, n_spike, n_gpot, steps): """ Benchmark inter-LPU communication throughput. Each LPU is configured to use a different local GPU. Parameters ---------- n_lpu : int Number of LPUs. Must be at least 2 and no greater than the number of local GPUs. n_spike : int Total number of input and output spiking ports any single LPU exposes to any other LPU. Each LPU will therefore have 2*n_spike*(n_lpu-1) total spiking ports. n_gpot : int Total number of input and output graded potential ports any single LPU exposes to any other LPU. Each LPU will therefore have 2*n_gpot*(n_lpu-1) total graded potential ports. steps : int Number of steps to execute. Returns ------- average_throughput, total_throughput : float Average per-step and total received data throughput in bytes/seconds. exec_time : float Execution time in seconds. """ # Time everything starting with manager initialization: start_all = time.time() # Set up manager: man = Manager() # Generate selectors for configuring modules and patterns: mod_sels, pat_sels = gen_sels(n_lpu, n_spike, n_gpot) # Set up modules: for i in xrange(n_lpu): lpu_i = 'lpu%s' % i sel, sel_in, sel_out, sel_gpot, sel_spike = mod_sels[lpu_i] man.add(MyModule, lpu_i, sel, sel_in, sel_out, sel_gpot, sel_spike, None, None, ['interface', 'io', 'type'], CTRL_TAG, GPOT_TAG, SPIKE_TAG, time_sync=True) # Set up connections between module pairs: for i, j in itertools.combinations(xrange(n_lpu), 2): lpu_i = 'lpu%s' % i lpu_j = 'lpu%s' % j sel_from, sel_to, sel_in_i, sel_out_i, sel_gpot_i, sel_spike_i, \ sel_in_j, sel_out_j, sel_gpot_j, sel_spike_j = pat_sels[(lpu_i, lpu_j)] pat = Pattern.from_concat(sel_from, sel_to, from_sel=sel_from, to_sel=sel_to, data=1) pat.interface[sel_in_i, 'interface', 'io'] = [0, 'in'] pat.interface[sel_out_i, 'interface', 'io'] = [0, 'out'] pat.interface[sel_gpot_i, 'interface', 'type'] = [0, 'gpot'] pat.interface[sel_spike_i, 'interface', 'type'] = [0, 'spike'] pat.interface[sel_in_j, 'interface', 'io'] = [1, 'in'] pat.interface[sel_out_j, 'interface', 'io'] = [1, 'out'] pat.interface[sel_gpot_j, 'interface', 'type'] = [1, 'gpot'] pat.interface[sel_spike_j, 'interface', 'type'] = [1, 'spike'] man.connect(lpu_i, lpu_j, pat, 0, 1, compat_check=False) man.spawn() start_main = time.time() man.start(steps) man.wait() stop_main = time.time() return man.average_step_sync_time, (time.time()-start_all), (stop_main-start_main), \ (man.stop_time-man.start_time)
def run_test(m0_sel_in_gpot, m0_sel_in_spike, m0_sel_out_gpot, m0_sel_out_spike, m1_sel_in_gpot, m1_sel_in_spike, m1_sel_out_gpot, m1_sel_out_spike): # Create test module classes with a queue installed in the destination # module to check that data was correctly propagated: class TestModule0(TestModule): def __init__(self, *args, **kwargs): super(TestModule0, self).__init__(*args, **kwargs) self.q = Queue() def run_step(self): self.log_info('saving data to queue before run step') if self.steps > 0: self.q.put( (self.pm['gpot'][self._out_port_dict['gpot']['m1']].copy(), self.pm['spike'][self._out_port_dict['spike'] ['m1']].copy())) super(TestModule0, self).run_step() class TestModule1(TestModule): def __init__(self, *args, **kwargs): super(TestModule1, self).__init__(*args, **kwargs) self.q = Queue() def run_step(self): super(TestModule1, self).run_step() self.log_info('saving data to queue after run step') if self.steps > 0: self.q.put( (self.pm['gpot'][self._in_port_dict['gpot']['m0']].copy(), self.pm['spike'][self._in_port_dict['spike'] ['m0']].copy())) m0_sel_gpot = m0_sel_in_gpot + m0_sel_out_gpot m0_sel_spike = m0_sel_in_spike + m0_sel_out_spike m0_sel = m0_sel_in_gpot + m0_sel_in_spike + m0_sel_out_gpot + m0_sel_out_spike m0_data_gpot = np.ones(len(m0_sel_gpot), np.double) m0_data_spike = np.ones(len(m0_sel_spike), np.int32) m1_sel_gpot = m1_sel_in_gpot + m1_sel_out_gpot m1_sel_spike = m1_sel_in_spike + m1_sel_out_spike m1_sel = m1_sel_in_gpot + m1_sel_in_spike + m1_sel_out_gpot + m1_sel_out_spike m1_data_gpot = np.zeros(len(m1_sel_gpot), np.double) m1_data_spike = np.zeros(len(m1_sel_spike), np.int32) # Instantiate manager and broker: man = Manager(get_random_port(), get_random_port(), get_random_port()) man.add_brok() # Add modules: m0 = TestModule0(m0_sel, m0_sel_in_gpot, m0_sel_in_spike, m0_sel_out_gpot, m0_sel_out_spike, m0_data_gpot, m0_data_spike, man.port_data, man.port_ctrl, man.port_time, id='m0') man.add_mod(m0) m1 = TestModule1(m1_sel, m1_sel_in_gpot, m1_sel_in_spike, m1_sel_out_gpot, m1_sel_out_spike, m1_data_gpot, m1_data_spike, man.port_data, man.port_ctrl, man.port_time, id='m1') man.add_mod(m1) # Connect the modules: pat = Pattern(m0_sel, m1_sel) pat.interface[m0_sel_in_gpot] = [0, 'in', 'gpot'] pat.interface[m0_sel_out_gpot] = [0, 'out', 'gpot'] pat.interface[m0_sel_in_spike] = [0, 'in', 'spike'] pat.interface[m0_sel_out_spike] = [0, 'out', 'spike'] pat.interface[m1_sel_in_gpot] = [1, 'in', 'gpot'] pat.interface[m1_sel_out_gpot] = [1, 'out', 'gpot'] pat.interface[m1_sel_in_spike] = [1, 'in', 'spike'] pat.interface[m1_sel_out_spike] = [1, 'out', 'spike'] for sel_from, sel_to in zip(m0_sel_out_gpot, m1_sel_in_gpot): if not (sel_from == ((), ) or sel_to == ((), )): pat[sel_from, sel_to] = 1 for sel_from, sel_to in zip(m0_sel_out_spike, m1_sel_in_spike): if not (sel_from == ((), ) or sel_to == ((), )): pat[sel_from, sel_to] = 1 man.connect(m0, m1, pat, 0, 1) # Execute exactly two steps; m0 transmits data during the first step, which # should be received by m1 during the second step: man.start(steps=2) man.stop() # Forcibly terminate all processes that are still alive: if m0.is_alive(): m0.terminate() if m1.is_alive(): m1.terminate() for b in man.brokers.values(): if b.is_alive(): b.terminate() # Check that data was propagated correctly: m0_data_gpot_after, m0_data_spike_after = m0.q.get() m1_data_gpot_after, m1_data_spike_after = m1.q.get() assert all(m0_data_gpot_after == m1_data_gpot_after) assert all(m0_data_spike_after == m1_data_spike_after)
class test_core_gpu(TestCase): def setUp(self): self.man = Manager() def test_transmit_spikes_one_to_one(self): m1_sel_in_gpot = Selector('') m1_sel_out_gpot = Selector('') m1_sel_in_spike = Selector('') m1_sel_out_spike = Selector('/m1/out/spike[0:4]') m1_sel, m1_sel_in, m1_sel_out, m1_sel_gpot, m1_sel_spike = \ make_sels(m1_sel_in_gpot, m1_sel_out_gpot, m1_sel_in_spike, m1_sel_out_spike) N1_gpot = SelectorMethods.count_ports(m1_sel_gpot) N1_spike = SelectorMethods.count_ports(m1_sel_spike) m2_sel_in_gpot = Selector('') m2_sel_out_gpot = Selector('') m2_sel_in_spike = Selector('/m2/in/spike[0:4]') m2_sel_out_spike = Selector('') m2_sel, m2_sel_in, m2_sel_out, m2_sel_gpot, m2_sel_spike = \ make_sels(m2_sel_in_gpot, m2_sel_out_gpot, m2_sel_in_spike, m2_sel_out_spike) N2_gpot = SelectorMethods.count_ports(m2_sel_gpot) N2_spike = SelectorMethods.count_ports(m2_sel_spike) m1_id = 'm1' self.man.add(MyModule1, m1_id, m1_sel, m1_sel_in, m1_sel_out, m1_sel_gpot, m1_sel_spike, np.zeros(N1_gpot, dtype=np.double), np.zeros(N1_spike, dtype=int), device=0, debug=debug, out_spike_data=[0, 0, 1, 1]) f, out_file_name = tempfile.mkstemp() os.close(f) m2_id = 'm2' self.man.add(MyModule2, m2_id, m2_sel, m2_sel_in, m2_sel_out, m2_sel_gpot, m2_sel_spike, np.zeros(N2_gpot, dtype=np.double), np.zeros(N2_spike, dtype=int), device=1, debug=debug, out_file_name=out_file_name) pat12 = Pattern(m1_sel, m2_sel) pat12.interface[m1_sel_out_gpot] = [0, 'in', 'gpot'] pat12.interface[m1_sel_in_gpot] = [0, 'out', 'gpot'] pat12.interface[m1_sel_out_spike] = [0, 'in', 'spike'] pat12.interface[m1_sel_in_spike] = [0, 'out', 'spike'] pat12.interface[m2_sel_in_gpot] = [1, 'out', 'gpot'] pat12.interface[m2_sel_out_gpot] = [1, 'in', 'gpot'] pat12.interface[m2_sel_in_spike] = [1, 'out', 'spike'] pat12.interface[m2_sel_out_spike] = [1, 'in', 'spike'] pat12['/m1/out/spike[0]', '/m2/in/spike[0]'] = 1 pat12['/m1/out/spike[1]', '/m2/in/spike[1]'] = 1 pat12['/m1/out/spike[2]', '/m2/in/spike[2]'] = 1 pat12['/m1/out/spike[3]', '/m2/in/spike[3]'] = 1 self.man.connect(m1_id, m2_id, pat12, 0, 1) # Run emulation for 2 steps: self.man.spawn() self.man.start(2) self.man.wait() # Get output of m2: with open(out_file_name, 'r') as f: output = pickle.load(f) os.remove(out_file_name) self.assertSequenceEqual(list(output), [0, 0, 1, 1]) def test_transmit_spikes_one_to_many(self): m1_sel_in_gpot = Selector('') m1_sel_out_gpot = Selector('') m1_sel_in_spike = Selector('') m1_sel_out_spike = Selector('/m1/out/spike[0:4]') m1_sel, m1_sel_in, m1_sel_out, m1_sel_gpot, m1_sel_spike = \ make_sels(m1_sel_in_gpot, m1_sel_out_gpot, m1_sel_in_spike, m1_sel_out_spike) N1_gpot = SelectorMethods.count_ports(m1_sel_gpot) N1_spike = SelectorMethods.count_ports(m1_sel_spike) m2_sel_in_gpot = Selector('') m2_sel_out_gpot = Selector('') m2_sel_in_spike = Selector('/m2/in/spike[0:4]') m2_sel_out_spike = Selector('') m2_sel, m2_sel_in, m2_sel_out, m2_sel_gpot, m2_sel_spike = \ make_sels(m2_sel_in_gpot, m2_sel_out_gpot, m2_sel_in_spike, m2_sel_out_spike) N2_gpot = SelectorMethods.count_ports(m2_sel_gpot) N2_spike = SelectorMethods.count_ports(m2_sel_spike) m1_id = 'm1' self.man.add(MyModule1, m1_id, m1_sel, m1_sel_in, m1_sel_out, m1_sel_gpot, m1_sel_spike, np.zeros(N1_gpot, dtype=np.double), np.zeros(N1_spike, dtype=int), device=0, debug=debug, out_spike_data=[1, 0, 0, 0]) f, out_file_name = tempfile.mkstemp() os.close(f) m2_id = 'm2' self.man.add(MyModule2, m2_id, m2_sel, m2_sel_in, m2_sel_out, m2_sel_gpot, m2_sel_spike, np.zeros(N2_gpot, dtype=np.double), np.zeros(N2_spike, dtype=int), device=1, debug=debug, out_file_name=out_file_name) pat12 = Pattern(m1_sel, m2_sel) pat12.interface[m1_sel_out_gpot] = [0, 'in', 'gpot'] pat12.interface[m1_sel_in_gpot] = [0, 'out', 'gpot'] pat12.interface[m1_sel_out_spike] = [0, 'in', 'spike'] pat12.interface[m1_sel_in_spike] = [0, 'out', 'spike'] pat12.interface[m2_sel_in_gpot] = [1, 'out', 'gpot'] pat12.interface[m2_sel_out_gpot] = [1, 'in', 'gpot'] pat12.interface[m2_sel_in_spike] = [1, 'out', 'spike'] pat12.interface[m2_sel_out_spike] = [1, 'in', 'spike'] pat12['/m1/out/spike[0]', '/m2/in/spike[0]'] = 1 pat12['/m1/out/spike[0]', '/m2/in/spike[1]'] = 1 pat12['/m1/out/spike[0]', '/m2/in/spike[2]'] = 1 pat12['/m1/out/spike[0]', '/m2/in/spike[3]'] = 1 self.man.connect(m1_id, m2_id, pat12, 0, 1) # Run emulation for 2 steps: self.man.spawn() self.man.start(2) self.man.wait() # Get output of m2: with open(out_file_name, 'r') as f: output = pickle.load(f) os.remove(out_file_name) self.assertSequenceEqual(list(output), [1, 1, 1, 1])
def run_test(m0_sel_in_gpot, m0_sel_in_spike, m0_sel_out_gpot, m0_sel_out_spike, m1_sel_in_gpot, m1_sel_in_spike, m1_sel_out_gpot, m1_sel_out_spike): # Create test module classes with a queue installed in the destination # module to check that data was correctly propagated: class TestModule0(TestModule): def __init__(self, *args, **kwargs): super(TestModule0, self).__init__(*args, **kwargs) self.q = Queue() def run_step(self): self.log_info('saving data to queue before run step') if self.steps > 0: self.q.put((self.pm['gpot'][self._out_port_dict['gpot']['m1']].copy(), self.pm['spike'][self._out_port_dict['spike']['m1']].copy())) super(TestModule0, self).run_step() class TestModule1(TestModule): def __init__(self, *args, **kwargs): super(TestModule1, self).__init__(*args, **kwargs) self.q = Queue() def run_step(self): super(TestModule1, self).run_step() self.log_info('saving data to queue after run step') if self.steps > 0: self.q.put((self.pm['gpot'][self._in_port_dict['gpot']['m0']].copy(), self.pm['spike'][self._in_port_dict['spike']['m0']].copy())) m0_sel_gpot = m0_sel_in_gpot+m0_sel_out_gpot m0_sel_spike = m0_sel_in_spike+m0_sel_out_spike m0_sel = m0_sel_in_gpot+m0_sel_in_spike+m0_sel_out_gpot+m0_sel_out_spike m0_data_gpot = np.ones(len(m0_sel_gpot), np.double) m0_data_spike = np.ones(len(m0_sel_spike), np.int32) m1_sel_gpot = m1_sel_in_gpot+m1_sel_out_gpot m1_sel_spike = m1_sel_in_spike+m1_sel_out_spike m1_sel = m1_sel_in_gpot+m1_sel_in_spike+m1_sel_out_gpot+m1_sel_out_spike m1_data_gpot = np.zeros(len(m1_sel_gpot), np.double) m1_data_spike = np.zeros(len(m1_sel_spike), np.int32) # Instantiate manager and broker: man = Manager(get_random_port(), get_random_port(), get_random_port()) man.add_brok() # Add modules: m0 = TestModule0(m0_sel, m0_sel_in_gpot, m0_sel_in_spike, m0_sel_out_gpot, m0_sel_out_spike, m0_data_gpot, m0_data_spike, man.port_data, man.port_ctrl, man.port_time, id='m0') man.add_mod(m0) m1 = TestModule1(m1_sel, m1_sel_in_gpot, m1_sel_in_spike, m1_sel_out_gpot, m1_sel_out_spike, m1_data_gpot, m1_data_spike, man.port_data, man.port_ctrl, man.port_time, id='m1') man.add_mod(m1) # Connect the modules: pat = Pattern(m0_sel, m1_sel) pat.interface[m0_sel_in_gpot] = [0, 'in', 'gpot'] pat.interface[m0_sel_out_gpot] = [0, 'out', 'gpot'] pat.interface[m0_sel_in_spike] = [0, 'in', 'spike'] pat.interface[m0_sel_out_spike] = [0, 'out', 'spike'] pat.interface[m1_sel_in_gpot] = [1, 'in', 'gpot'] pat.interface[m1_sel_out_gpot] = [1, 'out', 'gpot'] pat.interface[m1_sel_in_spike] = [1, 'in', 'spike'] pat.interface[m1_sel_out_spike] = [1, 'out', 'spike'] for sel_from, sel_to in zip(m0_sel_out_gpot, m1_sel_in_gpot): if not (sel_from == ((),) or sel_to == ((),)): pat[sel_from, sel_to] = 1 for sel_from, sel_to in zip(m0_sel_out_spike, m1_sel_in_spike): if not (sel_from == ((),) or sel_to == ((),)): pat[sel_from, sel_to] = 1 man.connect(m0, m1, pat, 0, 1) # Execute exactly two steps; m0 transmits data during the first step, which # should be received by m1 during the second step: man.start(steps=2) man.stop() # Forcibly terminate all processes that are still alive: if m0.is_alive(): m0.terminate() if m1.is_alive(): m1.terminate() for b in man.brokers.values(): if b.is_alive(): b.terminate() # Check that data was propagated correctly: m0_data_gpot_after, m0_data_spike_after = m0.q.get() m1_data_gpot_after, m1_data_spike_after = m1.q.get() assert all(m0_data_gpot_after == m1_data_gpot_after) assert all(m0_data_spike_after == m1_data_spike_after)
# Define synapses between spiking neurons in both directions: for id_src, id_dest, N_spike_src, N_spike_dest in \ [(lpu_dict[lpu_0]['id'], lpu_dict[lpu_1]['id'], N_spike_0, N_spike_1), (lpu_dict[lpu_1]['id'], lpu_dict[lpu_0]['id'], N_spike_1, N_spike_0)]: id_start = 0 for id, (i, j) in enumerate( itertools.product(xrange(N_spike_src), xrange(N_spike_dest)), id_start): conn[id_src, 'spike', i, id_dest, 'spike', j] = 1 conn[id_src, 'spike', i, id_dest, 'spike', j, 0, 'name'] = \ 'syn_%s:%s_%s:%s' % (id_src, i, id_dest, j) conn[id_src, 'spike', i, id_dest, 'spike', j, 0, 'model'] = 'AlphaSynapse' conn[id_src, 'spike', i, id_dest, 'spike', j, 0, 'ad'] = 0.19 * 1000 conn[id_src, 'spike', i, id_dest, 'spike', j, 0, 'ar'] = 1.1 * 100 conn[id_src, 'spike', i, id_dest, 'spike', j, 0, 'class'] = 0 # spike->spike conn[id_src, 'spike', i, id_dest, 'spike', j, 0, 'conductance'] = True conn[id_src, 'spike', i, id_dest, 'spike', j, 0, 'gmax'] = 0.003 conn[id_src, 'spike', i, id_dest, 'spike', j, 0, 'id'] = id conn[id_src, 'spike', i, id_dest, 'spike', j, 0, 'reverse'] = 0.065 id_start = id + 1 man.connect(lpu_dict[lpu_0]['lpu'], lpu_dict[lpu_1]['lpu'], conn) man.start(steps=steps) man.stop()