Skip to content

Commit f223677

Browse files
authored
Merge pull request VDOO-Connected-Trust#10 from fmagin/ci_build
Ci build
2 parents 05b9a83 + d100ae3 commit f223677

File tree

6 files changed

+120
-9
lines changed

6 files changed

+120
-9
lines changed

.github/workflows/publish.yml

Lines changed: 68 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,68 @@
1+
name: Publish Tagged Commit to PyPI
2+
3+
on:
4+
push:
5+
tags:
6+
- 'v*.*.*'
7+
8+
9+
jobs:
10+
build-n-publish:
11+
name: Build and publish Python Package
12+
runs-on: ubuntu-20.04
13+
steps:
14+
- uses: actions/checkout@v2
15+
- name: Set up JDK 1.11
16+
uses: actions/setup-java@v1
17+
with:
18+
java-version: 1.11
19+
20+
- name: Setup python
21+
uses: actions/setup-python@v2
22+
with:
23+
python-version: "2.7"
24+
25+
- uses: er28-0652/setup-ghidra@master
26+
with:
27+
version: "9.2.2"
28+
29+
- name: Prepare Jython Environment
30+
run:
31+
pip2.7 install --target="$GHIDRA_INSTALL_DIR/Ghidra/Features/Python/data/jython-2.7.2/Lib/site-packages" attrs typing
32+
33+
- name: Build Package
34+
run: |
35+
"$GHIDRA_INSTALL_DIR/support/analyzeHeadless" /tmp tmp -scriptPath $(pwd) -preScript generate_ghidra_pyi.py ./ ${GITHUB_REF#refs/*/}
36+
test -f setup.py # check manually, because analyzeHeadless doesn't fail on script failure
37+
test -d ghidra-stubs
38+
39+
- name: Set up Python 3.7
40+
uses: actions/setup-python@v2
41+
with:
42+
python-version: 3.7
43+
44+
- name: Install pypa/build
45+
run: >-
46+
python -m
47+
pip install
48+
wheel
49+
--user
50+
51+
- name: Build a binary wheel and a source tarball
52+
run: |
53+
python setup.py bdist_wheel --universal
54+
python setup.py sdist
55+
56+
# TODO: Setup publishing to PyPI by creating package and token and adding to GitHub secrets
57+
# - name: Publish distribution 📦 to PyPI
58+
# uses: pypa/gh-action-pypi-publish@master
59+
# with:
60+
# password: ${{ secrets.PYPI_API_TOKEN }}
61+
62+
63+
- name: Release on GitHub
64+
uses: softprops/action-gh-release@v1
65+
with:
66+
files: ./dist/*
67+
env:
68+
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}

.gitignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,2 +1,3 @@
11
*$py.class
22
*.pyi
3+
.idea

README.md

Lines changed: 28 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,9 +6,18 @@ Those stub files can later be used in PyCharm to enhance the development experie
66

77
You can either use the stubs released [here][latest-release], or follow the instructions below to generate them yourself.
88

9-
To use the stubs in PyCharm, follow the instructions in [Install, uninstall, and upgrade interpreter paths][interpreter-paths].
109

11-
### Using The Stubs
10+
## Using The Stubs
11+
12+
### Installation
13+
14+
The release contains [PEP 0561 stub package][pep-0561], which can simply be installed with `pip install ghidra-stubs*.whl`
15+
into the environment in which the real `ghidra` module is available. Any conformant tool will then use the stub package
16+
for type analysis purposes.
17+
18+
If you want to manually add the stub files to PyCharm, follow the instructions in [Install, uninstall, and upgrade interpreter paths][interpreter-paths].
19+
20+
### Usage
1221

1322
Once installed, all you need to do is import the Ghidra modules as usual, and PyCharm will do the rest.
1423

@@ -22,11 +31,27 @@ But the `.pyi` gives PyCharm all the information it needs to help you.
2231

2332
```python
2433
try:
25-
from ghidra_builtins import *
34+
from ghidra.ghidra_builtins import *
2635
except:
2736
pass
2837
```
2938

39+
If you are using [ghidra_bridge](https://github.com/justfoxing/ghidra_bridge) from a Python 3 environment where no real `ghidra` module
40+
exists you can use a snippet like the following:
41+
42+
```python
43+
import typing
44+
if typing.TYPE_CHECKING:
45+
import ghidra
46+
from ghidra.ghidra_builtins import *
47+
else:
48+
b = ghidra_bridge.GhidraBridge(namespace=globals())
49+
50+
# actual code follows here
51+
```
52+
53+
`typing.TYPE_CHECKING` is a special value that is always `False` at runtime but `True` during any kind of type checking or completion.
54+
3055
Once done, just code & enjoy.
3156

3257
![Pycharm Demo][pycharm-demo]

generate_ghidra_pyi.py

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,11 @@
44
import type_formatter
55

66
import ghidra
7+
# Make this script work with the stubs in an IDE
8+
try:
9+
from ghidra.ghidra_builtins import *
10+
except:
11+
pass
712
from __main__ import askDirectory, askYesNo, getGhidraVersion
813

914
from generate_stub_package import generate_package
@@ -35,7 +40,16 @@ def main():
3540
ghidra_package = type_extractor.Package.from_package(ghidra)
3641
type_formatter.create_type_hints(pyi_root, ghidra_package)
3742

38-
generate_package(pyi_root, getGhidraVersion())
43+
package_version = "DEV"
44+
if isRunningHeadless():
45+
# We are running in an headless environment and this might be an automated CI build
46+
# so we try getting an extra argument that is supposed to be the git commit tag so the package version is a combination
47+
# of the ghidra version and the version of the stub generating code
48+
try:
49+
package_version = askString("Package version", "Please specify package version")
50+
except:
51+
pass
52+
generate_package(pyi_root, getGhidraVersion(), stub_version=package_version)
3953

4054
if __name__ == '__main__':
4155
main()

generate_stub_package.py

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
import shutil
33

44

5-
def generate_package(pyi_root, ghidra_version):
5+
def generate_package(pyi_root, ghidra_version, stub_version="DEV"):
66

77
setup_code = """
88
from setuptools import setup
@@ -19,11 +19,12 @@ def find_stub_files():
1919
return result
2020
2121
setup(name= 'ghidra-stubs',
22-
version='{ghidra_version}',
22+
version='{ghidra_version}_{stub_version}',
2323
author='Tamir Bahar',
2424
packages=['ghidra-stubs'],
2525
package_data={{'ghidra-stubs': find_stub_files()}})
26-
""".format(ghidra_version=ghidra_version)
26+
""".format(ghidra_version=ghidra_version,
27+
stub_version=stub_version)
2728

2829
stub_folder = os.path.join(pyi_root, 'ghidra-stubs')
2930
os.rename(os.path.join(pyi_root, 'ghidra'), stub_folder)

type_extractor.py

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,8 @@ def get_members(obj):
3939
except java.lang.IllegalArgumentException:
4040
# Some values cannot be converted to Python types, so we are stuck.
4141
pass
42+
except java.lang.NoClassDefFoundError:
43+
pass
4244

4345
# If something is in `__dict__` we want it directly from there.
4446
# Attribute resolution destroys reflection info when class fields are involved.
@@ -86,10 +88,10 @@ def from_reflected_args(reflected_args, ctor_for=None, docs=None):
8688
if ctor_for is not None:
8789
return_type = ctor_for
8890
else:
89-
return_type = reflected_args.data.getReturnType()
91+
return_type = reflected_args.method.getReturnType()
9092

9193
return_type = BasicType.from_type(return_type)
92-
argument_types = map(BasicType.from_type, reflected_args.data.getParameterTypes())
94+
argument_types = map(BasicType.from_type, reflected_args.method.getParameterTypes())
9395

9496
argument_names = get_argument_names(argument_types, docs)
9597

0 commit comments

Comments
 (0)