/ ghidra / YankCurrentFunctionSymbol.py
YankCurrentFunctionSymbol.py
 1  #Copy the current function as a Binana symbol entry to your clipboard
 2  # @runtime Jython
 3  # @category Binana
 4  # @author Thunderbrew 
 5  # @keybinding Shift-F
 6  # @menupath 
 7  # @toolbar logo.png
 8  
 9  from ghidra.program.model.symbol import SymbolType
10  from java.awt import Toolkit
11  from java.awt.datatransfer import StringSelection
12  from ghidra.app.decompiler import DecompInterface
13  from ghidra.util.task import ConsoleTaskMonitor
14  
15  def yank_to_clipboard(text):
16      selection = StringSelection(text)
17      clipboard = Toolkit.getDefaultToolkit().getSystemClipboard()
18      clipboard.setContents(selection, None)
19  
20  def get_high_function_signature(func):
21      """Uses the Decompiler to get the refined signature."""
22      if func is None:
23          return ""
24          
25      iface = DecompInterface()
26      iface.openProgram(currentProgram)
27      
28      results = iface.decompileFunction(func, 30, ConsoleTaskMonitor())
29      high_func = results.getHighFunction()
30      
31      if high_func is None:
32          return 
33  
34      ret_type = high_func.getFunctionPrototype().getReturnType().getName().replace(" *", "*")
35  
36      call_conv = high_func.getFunctionPrototype().getModelName()
37  
38      params = []
39      num_params = high_func.getFunctionPrototype().getNumParams()
40      for i in range(num_params):
41          p = high_func.getFunctionPrototype().getParam(i)
42          params.append("{} {}".format(p.getDataType().getName().replace(" *", "*"), p.getName()))
43      
44      param_str = "(" + (", ".join(params)) + ")"
45      return ret_type + " " + call_conv + " func" + param_str
46  
47  def get_symbol_entry_for_function(func):
48      name = func.getName()
49      
50      entry_addr = func.getEntryPoint().toString().upper()[-8:]
51      body = func.getBody()
52      end_addr = (body.getMaxAddress().add(1)).toString().upper()[-8:]
53      
54      full_signature = get_high_function_signature(func)
55  
56      output = "{} {} f end={} type=\"{}\"".format(
57          name, 
58          entry_addr, 
59          end_addr, 
60          full_signature
61      ) 
62      return output
63  
64  def yank_current_function_symbol():
65      listing = currentProgram.getListing()
66      func = listing.getFunctionContaining(currentAddress)
67  
68      if func is None:
69          print("No function found at the current cursor position.")
70          return
71      output = get_symbol_entry_for_function(func)
72      yank_to_clipboard(output)
73      print("Copied to clipboard: {}".format(output))
74  
75  yank_current_function_symbol()