Compare commits
399 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
505525134f | ||
|
|
7dd740f51a | ||
|
|
3d590f8eb6 | ||
|
|
42a5c6a19f | ||
|
|
2c4f6063a6 | ||
|
|
845767b1d7 | ||
|
|
3e144af127 | ||
|
|
45f470e3a7 | ||
|
|
42a5c60af6 | ||
|
|
29cebd1e1f | ||
|
|
4450f5a084 | ||
|
|
b8230e144a | ||
|
|
d500902eff | ||
|
|
b787de0163 | ||
|
|
2f0d525c2e | ||
|
|
3f0c65ebb2 | ||
|
|
f33796797d | ||
|
|
68a09b9804 | ||
|
|
5e5d149ca5 | ||
|
|
bdf1c275c4 | ||
|
|
439a69f413 | ||
|
|
a14974fbf2 | ||
|
|
1ecd9af2e1 | ||
|
|
c8cc2dac04 | ||
|
|
60dd33b48f | ||
|
|
8b7d8b7786 | ||
|
|
fb7ea7810e | ||
|
|
508e16aa80 | ||
|
|
a057db8756 | ||
|
|
a1c588bde8 | ||
|
|
9b17fdeae2 | ||
|
|
29c0c737ed | ||
|
|
be6986a7f6 | ||
|
|
63c03bb28c | ||
|
|
758f5b27c3 | ||
|
|
32bfb3d57e | ||
|
|
6bd8822a90 | ||
|
|
abf461a049 | ||
|
|
4e98055b9c | ||
|
|
e6ab5bd86d | ||
|
|
02e0651eab | ||
|
|
93be634673 | ||
|
|
a1978f661b | ||
|
|
9bda864fed | ||
|
|
b6903c6b99 | ||
|
|
1e7394135d | ||
|
|
61ccaab55b | ||
|
|
f17c3c52c4 | ||
|
|
f16e721d01 | ||
|
|
6dfdca2d19 | ||
|
|
ee848e66ac | ||
|
|
91e1fa6aff | ||
|
|
6049cf9047 | ||
|
|
e91366c328 | ||
|
|
d6a5aaf4ad | ||
|
|
fcf3f2abc7 | ||
|
|
ae77622026 | ||
|
|
878b395e20 | ||
|
|
92aee9b69c | ||
|
|
fe10ddc720 | ||
|
|
46899f042f | ||
|
|
d4249da131 | ||
|
|
6cae018066 | ||
|
|
95c1886df5 | ||
|
|
fbd8cb07ea | ||
|
|
4868903844 | ||
|
|
62e721b1c8 | ||
|
|
1ceaf1df22 | ||
|
|
21c9f7b7fb | ||
|
|
f5526f73c7 | ||
|
|
15fad2e841 | ||
|
|
3ecb43072d | ||
|
|
2fce2318ed | ||
|
|
226fd29af8 | ||
|
|
c48b39baab | ||
|
|
ed19a6960e | ||
|
|
11b4de63ee | ||
|
|
b9d1d52ab3 | ||
|
|
fe548e580d | ||
|
|
fd7d2765c8 | ||
|
|
a226a70383 | ||
|
|
519e69a7f8 | ||
|
|
3d599f8044 | ||
|
|
bbf0393008 | ||
|
|
f1a4af013a | ||
|
|
05af9f9810 | ||
|
|
f68aada9f8 | ||
|
|
52d60d9623 | ||
|
|
2ddf8a44bc | ||
|
|
281fbc2bee | ||
|
|
c174568081 | ||
|
|
f4a519c824 | ||
|
|
62e4e2f716 | ||
|
|
193e6dfc93 | ||
|
|
7596658e6c | ||
|
|
73d6bd8400 | ||
|
|
922fabd935 | ||
|
|
2f3d267439 | ||
|
|
bdaf7ff30b | ||
|
|
cfca98512a | ||
|
|
23d9e86c46 | ||
|
|
6ac6fb0192 | ||
|
|
aaa36b9d3b | ||
|
|
2c799a8ccf | ||
|
|
56a5a7d72e | ||
|
|
410f9dd759 | ||
|
|
ba45217756 | ||
|
|
5a5929048d | ||
|
|
bfc3c7fbf9 | ||
|
|
e151bd4cd1 | ||
|
|
bfe68520f4 | ||
|
|
45734c0b5c | ||
|
|
d689062fc3 | ||
|
|
881574ed39 | ||
|
|
0bd5aa873b | ||
|
|
51f3ac2376 | ||
|
|
e5802853c0 | ||
|
|
edb5e36916 | ||
|
|
33ba94e784 | ||
|
|
9c969e0026 | ||
|
|
858622a98d | ||
|
|
c673489461 | ||
|
|
53a39b6947 | ||
|
|
8f82d86a5d | ||
|
|
f607cd8bad | ||
|
|
5b0965dc53 | ||
|
|
0db78100cd | ||
|
|
2196f2259f | ||
|
|
55814cbda4 | ||
|
|
6fb48023f2 | ||
|
|
76c1800a53 | ||
|
|
3b2f01e974 | ||
|
|
db141e1f3f | ||
|
|
8ca8824165 | ||
|
|
2e49161415 | ||
|
|
e5f38a6fc1 | ||
|
|
8c105d87c1 | ||
|
|
8c2946a41b | ||
|
|
4f21915f35 | ||
|
|
585bdb549f | ||
|
|
8091c9e737 | ||
|
|
fc504e18d2 | ||
|
|
90c76bb992 | ||
|
|
3da1aa3ec6 | ||
|
|
0a0d72e016 | ||
|
|
550889808a | ||
|
|
1c1da6433a | ||
|
|
963d7958ea | ||
|
|
7031247614 | ||
|
|
07738e13ef | ||
|
|
3ab96aa1ee | ||
|
|
bdd3f6ed44 | ||
|
|
3328847e27 | ||
|
|
4a6f072361 | ||
|
|
5bbcdd121a | ||
|
|
8e89dc8aa9 | ||
|
|
c458b726b4 | ||
|
|
c0a156f347 | ||
|
|
8e12cd6b02 | ||
|
|
a6f92b8ff9 | ||
|
|
cdb1cf1b63 | ||
|
|
877b397e04 | ||
|
|
df13e3ab82 | ||
|
|
8536fe4987 | ||
|
|
eba08334d1 | ||
|
|
165a99fd83 | ||
|
|
6754a9f3da | ||
|
|
12b0d81dda | ||
|
|
95da7c1c87 | ||
|
|
c903785864 | ||
|
|
eae94c5f23 | ||
|
|
ddabfdca3d | ||
|
|
5cf6a30027 | ||
|
|
91c9b4e168 | ||
|
|
914a0c60b0 | ||
|
|
773fb7c75b | ||
|
|
afe20ffe92 | ||
|
|
0b72c0b25c | ||
|
|
f06899303c | ||
|
|
b121d1730b | ||
|
|
5d570b5140 | ||
|
|
980a537930 | ||
|
|
d700c78f6c | ||
|
|
c7abc03fee | ||
|
|
9f243563b9 | ||
|
|
5eac8d860a | ||
|
|
1c8f860b6e | ||
|
|
1226308f3d | ||
|
|
40dd25c122 | ||
|
|
fa71885cf9 | ||
|
|
2a7be0eabb | ||
|
|
ab7c828cfa | ||
|
|
e6f8cfb16c | ||
|
|
0283a42273 | ||
|
|
d1a6d29fdd | ||
|
|
ee15aa888f | ||
|
|
3cc975813d | ||
|
|
f226177bca | ||
|
|
995478adac | ||
|
|
62915d5af5 | ||
|
|
825e2eec51 | ||
|
|
b7f2bae2ef | ||
|
|
9b4701fed7 | ||
|
|
937e55eb46 | ||
|
|
7c003e9e7a | ||
|
|
f0f973eb00 | ||
|
|
f399dd3498 | ||
|
|
d2e5bb99ef | ||
|
|
77eeea95c7 | ||
|
|
056ad51c24 | ||
|
|
97e38255c6 | ||
|
|
88004cac76 | ||
|
|
1162a5f916 | ||
|
|
418c37dd52 | ||
|
|
b66827998d | ||
|
|
b195656900 | ||
|
|
2628ee98f3 | ||
|
|
176c0b2d36 | ||
|
|
4986592dd7 | ||
|
|
a4c4324ba3 | ||
|
|
6442ab2f20 | ||
|
|
c19786bdfb | ||
|
|
1b498128ef | ||
|
|
556939139b | ||
|
|
d5dfd37385 | ||
|
|
508b4d648d | ||
|
|
163813145d | ||
|
|
5baa1aaa2a | ||
|
|
59b7d5a9f4 | ||
|
|
bbd1187a9c | ||
|
|
3f65ae39af | ||
|
|
8bac9853fa | ||
|
|
301a6736ac | ||
|
|
55ee21421e | ||
|
|
1a4ca389cd | ||
|
|
27cfeefef1 | ||
|
|
cc357b2b7d | ||
|
|
6335ac6a47 | ||
|
|
e61ebb4eb9 | ||
|
|
a6b8edde62 | ||
|
|
a4450db277 | ||
|
|
b7e38e95f0 | ||
|
|
cda572fd59 | ||
|
|
af4a0ffa21 | ||
|
|
f786c86f77 | ||
|
|
55365b1d17 | ||
|
|
d605c850b7 | ||
|
|
5bb33ce420 | ||
|
|
39268c681f | ||
|
|
a2b82c18d7 | ||
|
|
83a9ab44bd | ||
|
|
3bf3a276de | ||
|
|
9a7fbaee00 | ||
|
|
6ed01f24be | ||
|
|
04428c5aed | ||
|
|
ba8e48be38 | ||
|
|
bc2613c42b | ||
|
|
ac71a45b3b | ||
|
|
30425a194e | ||
|
|
63e678928b | ||
|
|
e32896137e | ||
|
|
0787909045 | ||
|
|
1acfb53c4c | ||
|
|
46c7e53ca1 | ||
|
|
7228709616 | ||
|
|
2ca5d39f7d | ||
|
|
08583463be | ||
|
|
84d3f6ac9c | ||
|
|
0f8fc7bdee | ||
|
|
cc0ae5e229 | ||
|
|
5750447826 | ||
|
|
908f0047f8 | ||
|
|
e533903cee | ||
|
|
1be8052caa | ||
|
|
668ce4bd2d | ||
|
|
e7fd038493 | ||
|
|
03edb3bbbe | ||
|
|
307a1a295a | ||
|
|
446df58e92 | ||
|
|
1ad5caba93 | ||
|
|
9eddc0e4f0 | ||
|
|
087ba0d81d | ||
|
|
3c5cd8f38f | ||
|
|
367743530f | ||
|
|
7370ce2793 | ||
|
|
ba61b42ef5 | ||
|
|
f7e362dd90 | ||
|
|
66da072fd7 | ||
|
|
d763534208 | ||
|
|
ad05898543 | ||
|
|
f930f7878d | ||
|
|
d6a75c411b | ||
|
|
568a71e0dc | ||
|
|
c92e9aac2c | ||
|
|
3012c4a3ff | ||
|
|
ebe338ac9a | ||
|
|
a45523a48c | ||
|
|
5bfeea67d7 | ||
|
|
f35f15d36c | ||
|
|
057af792df | ||
|
|
41a850e7b2 | ||
|
|
6be70390a6 | ||
|
|
1cfe3ee9f8 | ||
|
|
c1927c985a | ||
|
|
309f42994b | ||
|
|
feb28ecace | ||
|
|
00f74b7f0a | ||
|
|
fcc0e1776b | ||
|
|
a5ec755c28 | ||
|
|
98945926ca | ||
|
|
d3e3767df4 | ||
|
|
de1281bb66 | ||
|
|
07e55c3d89 | ||
|
|
6e4ebeddf4 | ||
|
|
2b9fb88bf0 | ||
|
|
022965b9c7 | ||
|
|
6278718a24 | ||
|
|
1675daafcd | ||
|
|
ed5b6edf52 | ||
|
|
638caa355c | ||
|
|
78b2f9b455 | ||
|
|
2a35ffcc27 | ||
|
|
5eae8f9af6 | ||
|
|
25381e20d2 | ||
|
|
fc35ff5cd1 | ||
|
|
b10d00b426 | ||
|
|
c634dc25b4 | ||
|
|
2fb4561bf8 | ||
|
|
f167c6dcca | ||
|
|
555ace9e2e | ||
|
|
d07ffb36ad | ||
|
|
9e2b8b77c9 | ||
|
|
29e4af4fb2 | ||
|
|
91513a12b4 | ||
|
|
ee3f55dd41 | ||
|
|
c2e5a78076 | ||
|
|
da3ac3e93d | ||
|
|
278ebbc9bd | ||
|
|
546f93147e | ||
|
|
3e7bfbb45c | ||
|
|
c2cf0443ef | ||
|
|
59d68c6438 | ||
|
|
e0ee199bf1 | ||
|
|
c1bf895674 | ||
|
|
ea4d92e671 | ||
|
|
e3f56105d4 | ||
|
|
c447a87605 | ||
|
|
584e5b1f01 | ||
|
|
207dc4c112 | ||
|
|
6a3581f7a3 | ||
|
|
11e74975b3 | ||
|
|
75ef9ec524 | ||
|
|
9b742e777b | ||
|
|
5d93565e16 | ||
|
|
cebfe5c95b | ||
|
|
7881f3a53b | ||
|
|
56269bd52b | ||
|
|
68c43a2cc9 | ||
|
|
120b507c75 | ||
|
|
44fe7e8dc4 | ||
|
|
75d679f141 | ||
|
|
e9570f2400 | ||
|
|
5b8567310c | ||
|
|
f882221db3 | ||
|
|
8c4d7bd641 | ||
|
|
6a78695fde | ||
|
|
73ad16dedd | ||
|
|
dd98112c5a | ||
|
|
47521d3579 | ||
|
|
0c31300578 | ||
|
|
6340ff7da0 | ||
|
|
b66cb49d80 | ||
|
|
c884184220 | ||
|
|
091fee61e0 | ||
|
|
172a268e77 | ||
|
|
924715fe34 | ||
|
|
35a73b4cde | ||
|
|
238f9593f9 | ||
|
|
9e8b5703dc | ||
|
|
d8bd8be57e | ||
|
|
a4d4e8b3a9 | ||
|
|
703dd17e33 | ||
|
|
bc654a462e | ||
|
|
11535825c0 | ||
|
|
196df40c99 | ||
|
|
7aee6c3a15 | ||
|
|
372b566d23 | ||
|
|
9550354442 | ||
|
|
95c3ddfc39 | ||
|
|
bf4f2b6fa0 | ||
|
|
d3f75a92ad | ||
|
|
369495c8d3 | ||
|
|
dd52f71069 | ||
|
|
af8e2bc19d | ||
|
|
947e5591ea | ||
|
|
521376e8e8 | ||
|
|
55c0adb23d | ||
|
|
b20ad7047f | ||
|
|
fa3149c660 |
90
.github/workflows/go.yml
vendored
90
.github/workflows/go.yml
vendored
@@ -11,19 +11,38 @@ on:
|
|||||||
|
|
||||||
jobs:
|
jobs:
|
||||||
|
|
||||||
test-macos:
|
test:
|
||||||
runs-on: macos-latest
|
|
||||||
strategy:
|
strategy:
|
||||||
matrix:
|
matrix:
|
||||||
|
os: [macos-latest, ubuntu-latest]
|
||||||
llvm: [17]
|
llvm: [17]
|
||||||
|
runs-on: ${{ matrix.os }}
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@v4
|
- uses: actions/checkout@v4
|
||||||
|
|
||||||
- name: Update Homebrew
|
- name: Update Homebrew
|
||||||
if: matrix.llvm == 17 # needed as long as LLVM 17 is still fresh
|
# needed as long as LLVM 17 is still fresh
|
||||||
|
if: matrix.llvm == 17 && startsWith(matrix.os, 'macos')
|
||||||
run: brew update
|
run: brew update
|
||||||
- name: Install LLVM ${{ matrix.llvm }}
|
- name: Install LLVM ${{ matrix.llvm }} and bdw-gc
|
||||||
run: HOMEBREW_NO_AUTO_UPDATE=1 brew install llvm@${{ matrix.llvm }}
|
if: startsWith(matrix.os, 'macos')
|
||||||
|
run: |
|
||||||
|
HOMEBREW_NO_AUTO_UPDATE=1 brew install llvm@${{ matrix.llvm }} bdw-gc
|
||||||
|
echo `brew --prefix llvm@${{ matrix.llvm }}`/bin >> $GITHUB_PATH
|
||||||
|
- name: Install LLVM ${{ matrix.llvm }} and libgc-dev
|
||||||
|
if: startsWith(matrix.os, 'ubuntu')
|
||||||
|
run: |
|
||||||
|
echo 'deb http://apt.llvm.org/focal/ llvm-toolchain-focal-${{ matrix.llvm }} main' | sudo tee /etc/apt/sources.list.d/llvm.list
|
||||||
|
wget -O - https://apt.llvm.org/llvm-snapshot.gpg.key | sudo apt-key add -
|
||||||
|
sudo apt-get update
|
||||||
|
sudo apt-get install --no-install-recommends clang-${{ matrix.llvm }} llvm-${{ matrix.llvm }}-dev libgc-dev
|
||||||
|
echo /usr/lib/llvm-${{ matrix.llvm }}/bin >> $GITHUB_PATH
|
||||||
|
|
||||||
|
- name: Clang information
|
||||||
|
run: |
|
||||||
|
echo $PATH
|
||||||
|
which clang
|
||||||
|
clang --version
|
||||||
|
|
||||||
- name: Set up Go
|
- name: Set up Go
|
||||||
uses: actions/setup-go@v5
|
uses: actions/setup-go@v5
|
||||||
@@ -34,36 +53,39 @@ jobs:
|
|||||||
run: go build -v ./...
|
run: go build -v ./...
|
||||||
|
|
||||||
- name: Test
|
- name: Test
|
||||||
|
if: matrix.os != 'ubuntu-latest'
|
||||||
run: go test -v ./...
|
run: go test -v ./...
|
||||||
|
- name: Test with coverage
|
||||||
|
if: matrix.os == 'ubuntu-latest'
|
||||||
|
run: go test -v -coverprofile="coverage.txt" -covermode=atomic ./...
|
||||||
|
|
||||||
test-linux:
|
- name: Install
|
||||||
runs-on: ubuntu-20.04
|
run: go install ./...
|
||||||
strategy:
|
|
||||||
matrix:
|
- name: LLGO tests
|
||||||
llvm: [17]
|
if: matrix.os != 'ubuntu-latest'
|
||||||
steps:
|
run: |
|
||||||
- uses: actions/checkout@v4
|
echo "Test result on ${{ matrix.os }} with LLVM ${{ matrix.llvm }}" > result.md
|
||||||
|
LLGOROOT=$PWD bash .github/workflows/test_llgo.sh
|
||||||
|
|
||||||
|
- name: Test _demo and _pydemo
|
||||||
|
run: |
|
||||||
|
set +e
|
||||||
|
LLGOROOT=$PWD bash .github/workflows/test_demo.sh
|
||||||
|
exit 0
|
||||||
|
|
||||||
|
- name: Show test result
|
||||||
|
run: cat result.md
|
||||||
|
|
||||||
- name: Install LLVM ${{ matrix.llvm }}
|
- name: PR comment with test result
|
||||||
run: |
|
uses: thollander/actions-comment-pull-request@v2
|
||||||
echo 'deb http://apt.llvm.org/focal/ llvm-toolchain-focal-${{ matrix.llvm }} main' | sudo tee /etc/apt/sources.list.d/llvm.list
|
if: false
|
||||||
wget -O - https://apt.llvm.org/llvm-snapshot.gpg.key | sudo apt-key add -
|
with:
|
||||||
sudo apt-get update
|
filePath: result.md
|
||||||
sudo apt-get install --no-install-recommends llvm-${{ matrix.llvm }}-dev
|
comment_tag: test-result-on-${{ matrix.os }}-with-llvm-${{ matrix.llvm }}
|
||||||
|
|
||||||
- name: Set up Go
|
- name: Upload coverage reports to Codecov
|
||||||
uses: actions/setup-go@v5
|
uses: codecov/codecov-action@v4
|
||||||
with:
|
with:
|
||||||
go-version: '1.20'
|
token: ${{ secrets.CODECOV_TOKEN }}
|
||||||
|
slug: goplus/llgo
|
||||||
- name: Build
|
|
||||||
run: go build -v ./...
|
|
||||||
|
|
||||||
- name: Test
|
|
||||||
run: go test -v -coverprofile="coverage.txt" -covermode=atomic ./...
|
|
||||||
|
|
||||||
- name: Upload coverage reports to Codecov
|
|
||||||
uses: codecov/codecov-action@v4
|
|
||||||
with:
|
|
||||||
token: ${{ secrets.CODECOV_TOKEN }}
|
|
||||||
slug: goplus/llgo
|
|
||||||
|
|||||||
29
.github/workflows/test_demo.sh
vendored
Normal file
29
.github/workflows/test_demo.sh
vendored
Normal file
@@ -0,0 +1,29 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
# llgo run subdirectories under _demo and _pydemo
|
||||||
|
total=0
|
||||||
|
failed=0
|
||||||
|
failed_cases=""
|
||||||
|
for d in ./_demo/* ./_pydemo/*; do
|
||||||
|
total=$((total+1))
|
||||||
|
if [ -d "$d" ]; then
|
||||||
|
echo "Testing $d"
|
||||||
|
if ! llgo run -v "$d"; then
|
||||||
|
echo "FAIL"
|
||||||
|
failed=$((failed+1))
|
||||||
|
failed_cases="$failed_cases\n* :x: $d"
|
||||||
|
else
|
||||||
|
echo "PASS"
|
||||||
|
fi
|
||||||
|
fi
|
||||||
|
done
|
||||||
|
echo "=== Done"
|
||||||
|
echo "$((total-failed))/$total tests passed"
|
||||||
|
|
||||||
|
if [ "$failed" -ne 0 ]; then
|
||||||
|
echo ":bangbang: Failed demo cases:" | tee -a result.md
|
||||||
|
echo -e "$failed_cases" | tee -a result.md
|
||||||
|
exit 1
|
||||||
|
else
|
||||||
|
echo ":white_check_mark: All demo tests passed" | tee -a result.md
|
||||||
|
fi
|
||||||
38
.github/workflows/test_llgo.sh
vendored
Normal file
38
.github/workflows/test_llgo.sh
vendored
Normal file
@@ -0,0 +1,38 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
set -e
|
||||||
|
|
||||||
|
export LLGOROOT=$PWD
|
||||||
|
|
||||||
|
testcmd=/tmp/test
|
||||||
|
llgo build -o $testcmd ./_test
|
||||||
|
cases=$($testcmd)
|
||||||
|
total=$(echo "$cases" | wc -l | tr -d ' ')
|
||||||
|
failed=0
|
||||||
|
failed_cases=""
|
||||||
|
|
||||||
|
for idx in $(seq 1 $((total))); do
|
||||||
|
case=$(echo "$cases" | sed -n "${idx}p")
|
||||||
|
case_name=$(echo "$case" | cut -d',' -f2)
|
||||||
|
echo "=== Test case: $case_name"
|
||||||
|
set +e
|
||||||
|
out=$("$testcmd" "$((idx-1))" 2>&1)
|
||||||
|
exit_code=$?
|
||||||
|
set -e
|
||||||
|
if [ "${exit_code:-0}" -ne 0 ]; then
|
||||||
|
echo "failed: $out"
|
||||||
|
failed=$((failed+1))
|
||||||
|
failed_cases="$failed_cases\n* :x: $case_name"
|
||||||
|
else
|
||||||
|
echo "passed"
|
||||||
|
fi
|
||||||
|
done
|
||||||
|
echo "=== Done"
|
||||||
|
echo "$((total-failed))/$total tests passed"
|
||||||
|
|
||||||
|
if [ "$failed" -ne 0 ]; then
|
||||||
|
echo ":bangbang: Failed llgo cases:" | tee -a result.md
|
||||||
|
echo -e "$failed_cases" | tee -a result.md
|
||||||
|
exit 1
|
||||||
|
else
|
||||||
|
echo ":white_check_mark: All llgo tests passed" | tee -a result.md
|
||||||
|
fi
|
||||||
4
.gitignore
vendored
4
.gitignore
vendored
@@ -9,10 +9,12 @@
|
|||||||
*.dylib
|
*.dylib
|
||||||
|
|
||||||
test.db
|
test.db
|
||||||
llgo_autogen.ll
|
demo.ll
|
||||||
|
llgo_autogen*.ll
|
||||||
stories*.bin
|
stories*.bin
|
||||||
.DS_Store
|
.DS_Store
|
||||||
err.log
|
err.log
|
||||||
|
numpy.txt
|
||||||
|
|
||||||
_go/
|
_go/
|
||||||
_runtime/
|
_runtime/
|
||||||
|
|||||||
7
.gitmodules
vendored
7
.gitmodules
vendored
@@ -1,6 +1,3 @@
|
|||||||
[submodule "x/llama2/llama2.c"]
|
[submodule "c/llama2/llama2.c"]
|
||||||
path = x/llama2/llama2.c
|
path = c/llama2/llama2.c
|
||||||
url = https://github.com/karpathy/llama2.c.git
|
url = https://github.com/karpathy/llama2.c.git
|
||||||
[submodule "x/sqlite/sqlite"]
|
|
||||||
path = x/sqlite/sqlite
|
|
||||||
url = https://github.com/sqlite/sqlite.git
|
|
||||||
|
|||||||
217
README.md
217
README.md
@@ -8,7 +8,8 @@ llgo - A Go compiler based on LLVM
|
|||||||
[](https://pkg.go.dev/github.com/goplus/llgo)
|
[](https://pkg.go.dev/github.com/goplus/llgo)
|
||||||
[](https://github.com/goplus/gop)
|
[](https://github.com/goplus/gop)
|
||||||
|
|
||||||
This is a Go compiler based on LLVM in order to better integrate Go with the C ecosystem including Python. It's a subproject of [the Go+ project](https://github.com/goplus/gop).
|
LLGo is a Go compiler based on LLVM in order to better integrate Go with the C ecosystem including Python. It's a subproject of [the Go+ project](https://github.com/goplus/gop).
|
||||||
|
|
||||||
|
|
||||||
## C standard libary support
|
## C standard libary support
|
||||||
|
|
||||||
@@ -22,14 +23,44 @@ func main() {
|
|||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
This is a simple example of calling the C `printf` function to print `Hello world`. Here, `c.Str` is not a function for converting a Go string to a C string, but a built-in instruction supported by llgo for generating a C string constant.
|
This is a simple example of calling the C `printf` function to print `Hello world`. Here, `c.Str` is not a function for converting a Go string to a C string, but a built-in instruction supported by `llgo` for generating a C string constant.
|
||||||
|
|
||||||
|
The `_demo` directory contains some C standard libary related demos (it start with `_` to prevent the `go` command from compiling it):
|
||||||
|
|
||||||
|
* [hello](_demo/hello/hello.go): call C `printf` to print `Hello world`
|
||||||
|
* [concat](_demo/concat/concat.go): call C `fprintf` with `stderr`
|
||||||
|
* [qsort](_demo/qsort/qsort.go): call C function with a callback (eg. `qsort`)
|
||||||
|
|
||||||
|
To run these demos (If you haven't installed `llgo` yet, please refer to [How to install](#how-to-install)):
|
||||||
|
|
||||||
|
```sh
|
||||||
|
export LLGOROOT=`pwd`
|
||||||
|
cd <demo-directory> # eg. cd _demo/hello
|
||||||
|
llgo run .
|
||||||
|
```
|
||||||
|
|
||||||
See [github.com/goplus/llgo/c](https://pkg.go.dev/github.com/goplus/llgo/c) for more detials.
|
See [github.com/goplus/llgo/c](https://pkg.go.dev/github.com/goplus/llgo/c) for more detials.
|
||||||
|
|
||||||
|
|
||||||
## Python support
|
## Python support
|
||||||
|
|
||||||
You can import a Python library in llgo! For example:
|
You can import a Python library in LLGo!
|
||||||
|
|
||||||
|
And you can import any Python library into `llgo` through a program called `llpyg` (see [Development tools](#development-tools)). The following libraries have been included in `llgo`:
|
||||||
|
|
||||||
|
* [builtins](https://pkg.go.dev/github.com/goplus/llgo/py/std)
|
||||||
|
* [sys](https://pkg.go.dev/github.com/goplus/llgo/py/sys)
|
||||||
|
* [os](https://pkg.go.dev/github.com/goplus/llgo/py/os)
|
||||||
|
* [math](https://pkg.go.dev/github.com/goplus/llgo/py/math)
|
||||||
|
* [json](https://pkg.go.dev/github.com/goplus/llgo/py/json)
|
||||||
|
* [inspect](https://pkg.go.dev/github.com/goplus/llgo/py/inspect)
|
||||||
|
* [statistics](https://pkg.go.dev/github.com/goplus/llgo/py/statistics)
|
||||||
|
* [numpy](https://pkg.go.dev/github.com/goplus/llgo/py/numpy)
|
||||||
|
* [pandas](https://pkg.go.dev/github.com/goplus/llgo/py/pandas)
|
||||||
|
* [pytorch](https://pkg.go.dev/github.com/goplus/llgo/py/torch)
|
||||||
|
* [matplotlib](https://pkg.go.dev/github.com/goplus/llgo/py/matplotlib)
|
||||||
|
|
||||||
|
Here is an example using the Python `math` library:
|
||||||
|
|
||||||
```go
|
```go
|
||||||
package main
|
package main
|
||||||
@@ -46,12 +77,136 @@ func main() {
|
|||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
Here, We call `py.Float(2)` to create a Python floating point number 2, and pass it to Python’s `math.sqrt` to get `x`. Then use `x.Float64()` to convert the Python object to Go's `float64` type, and finally we print the value through C `printf`.
|
Here, We call `py.Float(2)` to create a Python number 2, and pass it to Python’s `math.sqrt` to get `x`. Then use `x.Float64()` to convert x to Go's `float64` type, and print the value through the C `printf` function.
|
||||||
|
|
||||||
|
Let's look at a slightly more complex example. For example, we use `numpy` to calculate:
|
||||||
|
|
||||||
|
```go
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/goplus/llgo/c"
|
||||||
|
"github.com/goplus/llgo/py"
|
||||||
|
"github.com/goplus/llgo/py/numpy"
|
||||||
|
)
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
a := py.List(
|
||||||
|
py.List(1.0, 2.0, 3.0),
|
||||||
|
py.List(4.0, 5.0, 6.0),
|
||||||
|
py.List(7.0, 8.0, 9.0),
|
||||||
|
)
|
||||||
|
b := py.List(
|
||||||
|
py.List(9.0, 8.0, 7.0),
|
||||||
|
py.List(6.0, 5.0, 4.0),
|
||||||
|
py.List(3.0, 2.0, 1.0),
|
||||||
|
)
|
||||||
|
x := numpy.Add(a, b)
|
||||||
|
c.Printf(c.Str("a+b = %s\n"), x.Str().CStr())
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
Here we define two 3x3 matrices a and b, add them to get x, and then print the result.
|
||||||
|
|
||||||
|
The `_pydemo` directory contains some python related demos:
|
||||||
|
|
||||||
|
* [callpy](_pydemo/callpy/callpy.go): call Python standard library function `math.sqrt`
|
||||||
|
* [pi](_pydemo/pi/pi.go): print python constants `math.pi`
|
||||||
|
* [statistics](_pydemo/statistics/statistics.go): define a python list and call `statistics.mean` to get the mean
|
||||||
|
* [matrix](_pydemo/matrix/matrix.go): a basic `numpy` demo
|
||||||
|
|
||||||
|
To run these demos, you need to set the `LLGO_LIB_PYTHON` environment variable first.
|
||||||
|
|
||||||
|
If Python is in the search path for `clang` linking, then `LLGO_LIB_PYTHON` only needs to be set to the name of the Python library. For example:
|
||||||
|
|
||||||
|
```sh
|
||||||
|
export LLGO_LIB_PYTHON=python3.12
|
||||||
|
```
|
||||||
|
|
||||||
|
You can also specify the path to tell `llgo` where the Python library is located:
|
||||||
|
|
||||||
|
```sh
|
||||||
|
export LLGO_LIB_PYTHON=/foo/bar/python3.12
|
||||||
|
```
|
||||||
|
|
||||||
|
For example, `/opt/homebrew/Frameworks/Python.framework/Versions/3.12/libpython3.12.dylib` is a typical python library location under macOS. So we should set it like this:
|
||||||
|
|
||||||
|
```sh
|
||||||
|
export LLGO_LIB_PYTHON=/opt/homebrew/Frameworks/Python.framework/Versions/3.12/python3.12
|
||||||
|
```
|
||||||
|
|
||||||
|
Note that the file name must be written in a platform-independent format, using `python3.12` instead of `libpython3.12.dylib`.
|
||||||
|
|
||||||
|
Then you can run the demos:
|
||||||
|
|
||||||
|
```sh
|
||||||
|
export LLGOROOT=`pwd`
|
||||||
|
cd <demo-directory> # eg. cd _pydemo/callpy
|
||||||
|
llgo run .
|
||||||
|
```
|
||||||
|
|
||||||
|
See [github.com/goplus/llgo/py](https://pkg.go.dev/github.com/goplus/llgo/py) for more detials.
|
||||||
|
|
||||||
|
|
||||||
## Other frequently used libraries
|
## Other frequently used libraries
|
||||||
|
|
||||||
TODO
|
LLGo can easily import any libraries from the C ecosystem. Currently, this import process is still manual, but in the future, it will be automated similar to Python library imports.
|
||||||
|
|
||||||
|
The currently supported libraries include:
|
||||||
|
|
||||||
|
* [llama2.c](https://pkg.go.dev/github.com/goplus/llgo/c/llama2)
|
||||||
|
* [cjson](https://pkg.go.dev/github.com/goplus/llgo/c/cjson)
|
||||||
|
* [sqlite](https://pkg.go.dev/github.com/goplus/llgo/c/sqlite)
|
||||||
|
|
||||||
|
Here are some examples related to them:
|
||||||
|
|
||||||
|
* [llama2-c](_demo/llama2-c): inference Llama 2 (It's the first llgo AI example)
|
||||||
|
* [mkjson](c/cjson/_demo/mkjson/mkjson.go): create a json object and print it
|
||||||
|
* [sqlitedemo](c/sqlite/_demo/sqlitedemo/demo.go): a basic sqlite demo
|
||||||
|
|
||||||
|
|
||||||
|
## Go syntax support
|
||||||
|
|
||||||
|
Common Go syntax is already supported. Except for the following, which needs to be improved:
|
||||||
|
|
||||||
|
* map (Very limited support)
|
||||||
|
* recover (Not supported yet)
|
||||||
|
* chan (Not supported yet)
|
||||||
|
* generics (Not supported yet)
|
||||||
|
|
||||||
|
Here are some examples related to Go syntax:
|
||||||
|
|
||||||
|
* [concat](_demo/concat/concat.go): define a variadic function
|
||||||
|
* [genints](_demo/genints/genints.go): various forms of closure usage (including C function, recv.method and anonymous function)
|
||||||
|
* [errors](_demo/errors/errors.go): demo to implement error interface
|
||||||
|
* [defer](_demo/defer/defer.go): defer demo
|
||||||
|
* [goroutine](_demo/goroutine/goroutine.go): goroutine demo
|
||||||
|
|
||||||
|
|
||||||
|
## Defer
|
||||||
|
|
||||||
|
LLGo defer does not support usage in loops. This is not a bug but a feature, because we think that using defer in a loop is a very unrecommended practice.
|
||||||
|
|
||||||
|
|
||||||
|
### Garbage Collection (GC)
|
||||||
|
|
||||||
|
By default, LLGo implements `gc` based on [bdwgc](https://www.hboehm.info/gc/) (also known as [libgc](https://www.hboehm.info/gc/)).
|
||||||
|
|
||||||
|
However, you can disable gc by specifying the `nogc` tag. For example:
|
||||||
|
|
||||||
|
```sh
|
||||||
|
llgo run -tags nogc .
|
||||||
|
```
|
||||||
|
|
||||||
|
|
||||||
|
## Go packages support
|
||||||
|
|
||||||
|
Here are the Go packages that can be imported correctly:
|
||||||
|
|
||||||
|
* [unsafe](https://pkg.go.dev/unsafe)
|
||||||
|
* [unicode](https://pkg.go.dev/unicode)
|
||||||
|
* [unicode/utf8](https://pkg.go.dev/unicode/utf8)
|
||||||
|
* [unicode/utf16](https://pkg.go.dev/unicode/utf16)
|
||||||
|
|
||||||
|
|
||||||
## How to install
|
## How to install
|
||||||
@@ -62,6 +217,7 @@ Follow these steps to generate the `llgo` command (its usage is the same as the
|
|||||||
|
|
||||||
```sh
|
```sh
|
||||||
brew update # execute if needed
|
brew update # execute if needed
|
||||||
|
brew install libgc
|
||||||
brew install llvm@17
|
brew install llvm@17
|
||||||
go install -v ./...
|
go install -v ./...
|
||||||
```
|
```
|
||||||
@@ -72,6 +228,7 @@ go install -v ./...
|
|||||||
echo 'deb http://apt.llvm.org/focal/ llvm-toolchain-focal-17 main' | sudo tee /etc/apt/sources.list.d/llvm.list
|
echo 'deb http://apt.llvm.org/focal/ llvm-toolchain-focal-17 main' | sudo tee /etc/apt/sources.list.d/llvm.list
|
||||||
wget -O - https://apt.llvm.org/llvm-snapshot.gpg.key | sudo apt-key add -
|
wget -O - https://apt.llvm.org/llvm-snapshot.gpg.key | sudo apt-key add -
|
||||||
sudo apt-get update # execute if needed
|
sudo apt-get update # execute if needed
|
||||||
|
sudo apt-get install libgc-dev
|
||||||
sudo apt-get install --no-install-recommends llvm-17-dev
|
sudo apt-get install --no-install-recommends llvm-17-dev
|
||||||
go install -v ./...
|
go install -v ./...
|
||||||
```
|
```
|
||||||
@@ -81,45 +238,27 @@ go install -v ./...
|
|||||||
TODO
|
TODO
|
||||||
|
|
||||||
|
|
||||||
## Demo
|
## Development tools
|
||||||
|
|
||||||
The `_demo` directory contains our demos (it start with `_` to prevent the `go` command from compiling it):
|
* [pydump](chore/_xtool/pydump): It's the first program compiled by `llgo` (NOT `go`) in a production environment. It outputs symbol information (functions, variables, and constants) from a Python library in JSON format, preparing for the generation of corresponding packages in `llgo`.
|
||||||
|
* [pysigfetch](https://github.com/goplus/hdq/tree/main/chore/pysigfetch): It generates symbol information by extracting information from Python's documentation site. This tool is not part of the `llgo` project, but we depend on it.
|
||||||
|
* [llpyg](chore/llpyg): It is used to automatically convert Python libraries into Go packages that `llgo` can import. It depends on `pydump` and `pysigfetch` to accomplish the task.
|
||||||
|
* [llgen](chore/llgen): It is used to compile Go packages into LLVM IR files (*.ll).
|
||||||
|
* [ssadump](chore/ssadump): It is a Go SSA builder and interpreter.
|
||||||
|
|
||||||
* [hello](_demo/hello/hello.go): call C printf to print `Hello world`
|
How do I generate these tools?
|
||||||
* [concat](_demo/concat/concat.go): call C fprintf with stderr, and Go variadic function
|
|
||||||
* [qsort](_demo/qsort/qsort.go): call C function with a callback (eg. qsort)
|
|
||||||
* [genints](_demo/genints/genints.go): various forms of closure usage (including C function, recv.method and anonymous function)
|
|
||||||
* [llama2-c](_demo/llama2-c): inference Llama 2 (It's the first llgo AI example)
|
|
||||||
|
|
||||||
And the `_pydemo` directory contains python related demos:
|
|
||||||
|
|
||||||
* [callpy](_pydemo/callpy/callpy.go): call Python standard library function `math.sqrt`
|
|
||||||
|
|
||||||
|
|
||||||
### How to run demos
|
|
||||||
|
|
||||||
To run the demos in directory `_demo`:
|
|
||||||
|
|
||||||
```sh
|
```sh
|
||||||
cd <demo-directory> # eg. cd _demo/genints
|
go install -v ./... # compile all tools except pydump
|
||||||
llgo run .
|
cd chore/_xtool
|
||||||
|
llgo install ./... # compile pydump
|
||||||
|
go install github.com/goplus/hdq/chore/pysigfetch@v0.8.1 # compile pysigfetch
|
||||||
```
|
```
|
||||||
|
|
||||||
To run the demos in directory `_pydemo`, you need to set the `LLGO_LIB_PYTHON` environment variable first. Assuming you use Python 3.12, and the `libpython3.12.so` (or `libpython3.12.dylib` or `python3.12.lib`) file is in the /foo/bar directory, then you need to set `LLGO_LIB_PYTHON` to:
|
## Key modules
|
||||||
|
|
||||||
```sh
|
Below are the key modules for understanding the implementation principles of `llgo`:
|
||||||
export LLGO_LIB_PYTHON=/foo/bar/python3.12
|
|
||||||
```
|
|
||||||
|
|
||||||
For example, `/opt/homebrew/Frameworks/Python.framework/Versions/3.12/libpython3.12.dylib` is a typical python lib location under macOS. So we should set it like this:
|
* [llgo/ssa](https://pkg.go.dev/github.com/goplus/llgo/ssa): It generates LLVM IR files (LLVM SSA) using the semantics (interfaces) of Go SSA. Although `LLVM SSA` and `Go SSA` are both IR languages, they work at completely different levels. `LLVM SSA` is closer to machine code, which abstracts different instruction sets. While `Go SSA` is closer to a high-level language. We can think of it as the instruction set of the `Go computer`. `llgo/ssa` is not just limited to the `llgo` compiler. If we view it as the high-level expressive power of `LLVM`, you'll find it very useful. Prior to `llgo/ssa`, you had to operate `LLVM` using machine code semantics. But now, with the advanced SSA form (in the semantics of Go SSA), you can conveniently utilize `LLVM`.
|
||||||
|
* [llgo/cl](https://pkg.go.dev/github.com/goplus/llgo/cl): It is the core of the llgo compiler. It converts a Go package into LLVM IR files. It depends on `llgo/ssa`.
|
||||||
```sh
|
* [llgo/internal/build](https://pkg.go.dev/github.com/goplus/llgo/internal/build): It strings together the entire compilation process of `llgo`. It depends on `llgo/ssa` and `llgo/cl`.
|
||||||
export LLGO_LIB_PYTHON=/opt/homebrew/Frameworks/Python.framework/Versions/3.12/python3.12
|
|
||||||
```
|
|
||||||
|
|
||||||
Then you can run the demos in directory `_pydemo`:
|
|
||||||
|
|
||||||
```sh
|
|
||||||
cd <demo-directory> # eg. cd _pydemo/callpy
|
|
||||||
llgo run .
|
|
||||||
```
|
|
||||||
|
|||||||
17
_demo/defer/defer.go
Normal file
17
_demo/defer/defer.go
Normal file
@@ -0,0 +1,17 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
func f(s string) bool {
|
||||||
|
return len(s) > 2
|
||||||
|
}
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
defer func() {
|
||||||
|
println("hi")
|
||||||
|
}()
|
||||||
|
if s := "hello"; f(s) {
|
||||||
|
defer println(s)
|
||||||
|
} else {
|
||||||
|
defer println("world")
|
||||||
|
}
|
||||||
|
defer println("bye")
|
||||||
|
}
|
||||||
22
_demo/errors/errors.go
Normal file
22
_demo/errors/errors.go
Normal file
@@ -0,0 +1,22 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
// New returns an error that formats as the given text.
|
||||||
|
// Each call to New returns a distinct error value even if the text is identical.
|
||||||
|
func New(text string) error {
|
||||||
|
return &errorString{text}
|
||||||
|
}
|
||||||
|
|
||||||
|
// errorString is a trivial implementation of error.
|
||||||
|
type errorString struct {
|
||||||
|
s string
|
||||||
|
}
|
||||||
|
|
||||||
|
func (e *errorString) Error() string {
|
||||||
|
return e.s
|
||||||
|
}
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
err := New("an error")
|
||||||
|
println(err)
|
||||||
|
println(err.Error())
|
||||||
|
}
|
||||||
12
_demo/goroutine/goroutine.go
Normal file
12
_demo/goroutine/goroutine.go
Normal file
@@ -0,0 +1,12 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
done := false
|
||||||
|
go func() {
|
||||||
|
println("Hello, goroutine")
|
||||||
|
done = true
|
||||||
|
}()
|
||||||
|
for !done {
|
||||||
|
print(".")
|
||||||
|
}
|
||||||
|
}
|
||||||
9
_demo/interf/foo/foo.go
Normal file
9
_demo/interf/foo/foo.go
Normal file
@@ -0,0 +1,9 @@
|
|||||||
|
package foo
|
||||||
|
|
||||||
|
func Bar() any {
|
||||||
|
return struct{ V int }{1}
|
||||||
|
}
|
||||||
|
|
||||||
|
func F() any {
|
||||||
|
return struct{ v int }{1}
|
||||||
|
}
|
||||||
35
_demo/interf/interf.go
Normal file
35
_demo/interf/interf.go
Normal file
@@ -0,0 +1,35 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/goplus/llgo/_demo/interf/foo"
|
||||||
|
)
|
||||||
|
|
||||||
|
func Foo() any {
|
||||||
|
return struct{ v int }{1}
|
||||||
|
}
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
v := Foo()
|
||||||
|
if x, ok := v.(struct{ v int }); ok {
|
||||||
|
println(x.v)
|
||||||
|
} else {
|
||||||
|
println("Foo: not ok")
|
||||||
|
}
|
||||||
|
bar := foo.Bar()
|
||||||
|
if x, ok := bar.(struct{ V int }); ok {
|
||||||
|
println(x.V)
|
||||||
|
} else {
|
||||||
|
println("Bar: not ok")
|
||||||
|
}
|
||||||
|
if x, ok := foo.F().(struct{ v int }); ok {
|
||||||
|
println(x.v)
|
||||||
|
} else {
|
||||||
|
println("F: not ok")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Expected output:
|
||||||
|
1
|
||||||
|
1
|
||||||
|
F: not ok
|
||||||
|
*/
|
||||||
@@ -2,7 +2,7 @@ package main
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"github.com/goplus/llgo/c"
|
"github.com/goplus/llgo/c"
|
||||||
"github.com/goplus/llgo/x/llama2"
|
"github.com/goplus/llgo/c/llama2"
|
||||||
)
|
)
|
||||||
|
|
||||||
func main() {
|
func main() {
|
||||||
|
|||||||
16
_demo/setjmp/setjmp.go
Normal file
16
_demo/setjmp/setjmp.go
Normal file
@@ -0,0 +1,16 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/goplus/llgo/c/setjmp"
|
||||||
|
)
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
var jb setjmp.SigjmpBuf
|
||||||
|
switch ret := setjmp.Sigsetjmp(&jb, 0); ret {
|
||||||
|
case 0:
|
||||||
|
println("Hello, setjmp!")
|
||||||
|
setjmp.Siglongjmp(&jb, 1)
|
||||||
|
default:
|
||||||
|
println("exception:", ret)
|
||||||
|
}
|
||||||
|
}
|
||||||
25
_demo/thread/thd.go
Normal file
25
_demo/thread/thd.go
Normal file
@@ -0,0 +1,25 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/goplus/llgo/c"
|
||||||
|
"github.com/goplus/llgo/c/pthread"
|
||||||
|
)
|
||||||
|
|
||||||
|
var key pthread.Key
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
key.Create(nil)
|
||||||
|
key.Set(c.Pointer(c.Str("main value\n")))
|
||||||
|
|
||||||
|
var thd pthread.Thread
|
||||||
|
pthread.Create(&thd, nil, func(arg c.Pointer) c.Pointer {
|
||||||
|
key.Set(c.Pointer(c.Str("thread value\n")))
|
||||||
|
c.Printf(c.Str("Hello, thread\nTLS: %s"), key.Get())
|
||||||
|
return c.Pointer(c.Str("Back to main\n"))
|
||||||
|
}, nil)
|
||||||
|
|
||||||
|
var retval c.Pointer
|
||||||
|
pthread.Join(thd, &retval)
|
||||||
|
|
||||||
|
c.Printf(c.Str("%sTLS: %s"), retval, key.Get())
|
||||||
|
}
|
||||||
22
_pydemo/matrix/matrix.go
Normal file
22
_pydemo/matrix/matrix.go
Normal file
@@ -0,0 +1,22 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/goplus/llgo/c"
|
||||||
|
"github.com/goplus/llgo/py"
|
||||||
|
"github.com/goplus/llgo/py/numpy"
|
||||||
|
)
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
a := py.List(
|
||||||
|
py.List(1.0, 2.0, 3.0),
|
||||||
|
py.List(4.0, 5.0, 6.0),
|
||||||
|
py.List(7.0, 8.0, 9.0),
|
||||||
|
)
|
||||||
|
b := py.List(
|
||||||
|
py.List(9.0, 8.0, 7.0),
|
||||||
|
py.List(6.0, 5.0, 4.0),
|
||||||
|
py.List(3.0, 2.0, 1.0),
|
||||||
|
)
|
||||||
|
x := numpy.Add(a, b)
|
||||||
|
c.Printf(c.Str("a+b = %s\n"), x.Str().CStr())
|
||||||
|
}
|
||||||
15
_pydemo/max/max.go
Normal file
15
_pydemo/max/max.go
Normal file
@@ -0,0 +1,15 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/goplus/llgo/py"
|
||||||
|
"github.com/goplus/llgo/py/std"
|
||||||
|
)
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
x := std.Max(py.Float(3.0), py.Float(9.0), py.Float(23.0), py.Float(100.0))
|
||||||
|
std.Print(x)
|
||||||
|
|
||||||
|
list := py.List(3.0, 9.0, 23.0, 100.0)
|
||||||
|
y := std.Max(std.Iter(list))
|
||||||
|
std.Print(y)
|
||||||
|
}
|
||||||
10
_pydemo/pi/pi.go
Normal file
10
_pydemo/pi/pi.go
Normal file
@@ -0,0 +1,10 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/goplus/llgo/c"
|
||||||
|
"github.com/goplus/llgo/py/math"
|
||||||
|
)
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
c.Printf(c.Str("pi = %f\n"), math.Pi.Float64())
|
||||||
|
}
|
||||||
11
_pydemo/print/print.go
Normal file
11
_pydemo/print/print.go
Normal file
@@ -0,0 +1,11 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/goplus/llgo/py"
|
||||||
|
"github.com/goplus/llgo/py/std"
|
||||||
|
)
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
x := py.Float(3.14)
|
||||||
|
std.Print(x)
|
||||||
|
}
|
||||||
13
_pydemo/statistics/statistics.go
Normal file
13
_pydemo/statistics/statistics.go
Normal file
@@ -0,0 +1,13 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/goplus/llgo/c"
|
||||||
|
"github.com/goplus/llgo/py"
|
||||||
|
"github.com/goplus/llgo/py/statistics"
|
||||||
|
)
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
list := py.List(1.0, 2.0, 3.0, 4.0, 4.0)
|
||||||
|
mean := statistics.Mean(list)
|
||||||
|
c.Printf(c.Str("mean(1, 2, 3, 4, 4) = %f\n"), mean.Float64())
|
||||||
|
}
|
||||||
16
_pydemo/tensor/tensor.go
Normal file
16
_pydemo/tensor/tensor.go
Normal file
@@ -0,0 +1,16 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/goplus/llgo/py"
|
||||||
|
"github.com/goplus/llgo/py/std"
|
||||||
|
"github.com/goplus/llgo/py/torch"
|
||||||
|
)
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
data := py.List(
|
||||||
|
py.List(1.0, 2.0),
|
||||||
|
py.List(3.0, 4.0),
|
||||||
|
)
|
||||||
|
x := torch.Tensor(data)
|
||||||
|
std.Print(x)
|
||||||
|
}
|
||||||
101
_test/bdwgc.go
Normal file
101
_test/bdwgc.go
Normal file
@@ -0,0 +1,101 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"unsafe"
|
||||||
|
|
||||||
|
"github.com/goplus/llgo/_test/testing"
|
||||||
|
"github.com/goplus/llgo/c"
|
||||||
|
"github.com/goplus/llgo/internal/runtime/bdwgc"
|
||||||
|
)
|
||||||
|
|
||||||
|
// ------ Test malloc ------
|
||||||
|
|
||||||
|
func TestMalloc(t *testing.T) {
|
||||||
|
pn := (*int)(bdwgc.Malloc(unsafe.Sizeof(int(0))))
|
||||||
|
*pn = 1 << 30
|
||||||
|
c.Printf(c.Str("value: %d, %x, %p, %p\n"), *pn, *pn, pn, &pn)
|
||||||
|
|
||||||
|
pl := (*int64)(bdwgc.Realloc(c.Pointer(pn), unsafe.Sizeof(int64(0))))
|
||||||
|
*pl = 1 << 60
|
||||||
|
c.Printf(c.Str("value: %lld, %llx, %p, %p\n"), *pl, *pl, pl, &pl)
|
||||||
|
|
||||||
|
bdwgc.Free(c.Pointer(pl))
|
||||||
|
}
|
||||||
|
|
||||||
|
// ------ Test finalizer ------
|
||||||
|
|
||||||
|
const (
|
||||||
|
RETURN_VALUE_FREED = 1 << 31
|
||||||
|
)
|
||||||
|
|
||||||
|
var called uint = 0
|
||||||
|
|
||||||
|
func setReturnValueFreed(pobj c.Pointer, clientData c.Pointer) {
|
||||||
|
called |= RETURN_VALUE_FREED
|
||||||
|
c.Printf(c.Str("called: %x\n"), called)
|
||||||
|
}
|
||||||
|
|
||||||
|
func setLoopValueFreed(pobj c.Pointer, clientData c.Pointer) {
|
||||||
|
pmask := (*uint)(clientData)
|
||||||
|
called |= *pmask
|
||||||
|
c.Printf(c.Str("called: %x\n"), called)
|
||||||
|
}
|
||||||
|
|
||||||
|
func isCalled(mask uint) bool {
|
||||||
|
return called&mask != 0
|
||||||
|
}
|
||||||
|
|
||||||
|
func returnValue() *int {
|
||||||
|
pn := bdwgc.Malloc(unsafe.Sizeof(int(0)))
|
||||||
|
bdwgc.RegisterFinalizer(pn, setReturnValueFreed, nil, nil, nil)
|
||||||
|
return (*int)(pn)
|
||||||
|
}
|
||||||
|
|
||||||
|
func callFunc() {
|
||||||
|
pn := returnValue()
|
||||||
|
*pn = 1 << 30
|
||||||
|
c.Printf(c.Str("value: %d, %x, %p, %p\n"), *pn, *pn, pn, &pn)
|
||||||
|
bdwgc.Gcollect()
|
||||||
|
check(!isCalled(RETURN_VALUE_FREED), c.Str("finalizer should not be called"))
|
||||||
|
}
|
||||||
|
|
||||||
|
func loop() {
|
||||||
|
for i := 0; i < 5; i++ {
|
||||||
|
p := bdwgc.Malloc(unsafe.Sizeof(int(0)))
|
||||||
|
pn := (*int)(p)
|
||||||
|
*pn = i
|
||||||
|
c.Printf(c.Str("value: %d, %x, %p, %p\n"), *pn, *pn, pn, &pn)
|
||||||
|
pflag := (*uint)(c.Malloc(unsafe.Sizeof(uint(0))))
|
||||||
|
*pflag = 1 << i
|
||||||
|
bdwgc.RegisterFinalizer(p, setLoopValueFreed, c.Pointer(pflag), nil, nil)
|
||||||
|
bdwgc.Gcollect()
|
||||||
|
check(!isCalled(1<<i), c.Str("finalizer should not be called"))
|
||||||
|
for j := 0; j < i; j++ {
|
||||||
|
check(isCalled(1<<j), c.Str("finalizers of previous objects should be called"))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Clear stack to avoid reference
|
||||||
|
func clearStack() {
|
||||||
|
p := c.Alloca(128)
|
||||||
|
c.Memset(p, 0, 128)
|
||||||
|
}
|
||||||
|
|
||||||
|
func check(b bool, msg *c.Char) {
|
||||||
|
if !b {
|
||||||
|
c.Printf(c.Str("check failed: %s\n"), msg)
|
||||||
|
panic("check failed")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestFinalizer(t *testing.T) {
|
||||||
|
bdwgc.Init()
|
||||||
|
|
||||||
|
callFunc()
|
||||||
|
clearStack()
|
||||||
|
bdwgc.Gcollect()
|
||||||
|
check(isCalled(RETURN_VALUE_FREED), c.Str("finalizer should be called"))
|
||||||
|
|
||||||
|
loop()
|
||||||
|
}
|
||||||
31
_test/main.go
Normal file
31
_test/main.go
Normal file
@@ -0,0 +1,31 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/goplus/llgo/_test/testing"
|
||||||
|
"github.com/goplus/llgo/c"
|
||||||
|
)
|
||||||
|
|
||||||
|
type TestCase struct {
|
||||||
|
Name string
|
||||||
|
F func(*testing.T)
|
||||||
|
}
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
tests := []TestCase{
|
||||||
|
{"TestMalloc", TestMalloc},
|
||||||
|
{"TestFinalizer", TestFinalizer},
|
||||||
|
}
|
||||||
|
if c.Argc == 1 {
|
||||||
|
for _, test := range tests {
|
||||||
|
c.Printf(c.Str("%s\n"), c.AllocaCStr(test.Name))
|
||||||
|
}
|
||||||
|
return
|
||||||
|
}
|
||||||
|
c.Fprintf(c.Stderr, c.Str("arg: %s\n"), c.Index(c.Argv, 1))
|
||||||
|
idx := int(c.Atoi(c.Index(c.Argv, 1)))
|
||||||
|
if idx < 0 || idx >= len(tests) {
|
||||||
|
c.Printf(c.Str("invalid test index %d"), idx)
|
||||||
|
panic("invalid test index")
|
||||||
|
}
|
||||||
|
tests[idx].F(nil)
|
||||||
|
}
|
||||||
4
_test/testing/testing.go
Normal file
4
_test/testing/testing.go
Normal file
@@ -0,0 +1,4 @@
|
|||||||
|
package testing
|
||||||
|
|
||||||
|
type T struct {
|
||||||
|
}
|
||||||
68
c/c.go
68
c/c.go
@@ -25,12 +25,17 @@ const (
|
|||||||
)
|
)
|
||||||
|
|
||||||
type (
|
type (
|
||||||
Char = int8
|
Char = int8
|
||||||
Int = C.int
|
Int = C.int
|
||||||
Uint = C.uint
|
Uint = C.uint
|
||||||
Float = float32
|
Long = int32
|
||||||
Pointer = unsafe.Pointer
|
Ulong = uint32
|
||||||
FilePtr = unsafe.Pointer
|
LongLong = int64
|
||||||
|
UlongLong = uint64
|
||||||
|
Float = float32
|
||||||
|
Double = float64
|
||||||
|
Pointer = unsafe.Pointer
|
||||||
|
FilePtr = unsafe.Pointer
|
||||||
)
|
)
|
||||||
|
|
||||||
type integer interface {
|
type integer interface {
|
||||||
@@ -52,12 +57,12 @@ func Alloca(size uintptr) Pointer
|
|||||||
//go:linkname AllocaCStr llgo.allocaCStr
|
//go:linkname AllocaCStr llgo.allocaCStr
|
||||||
func AllocaCStr(s string) *Char
|
func AllocaCStr(s string) *Char
|
||||||
|
|
||||||
//go:linkname Unreachable llgo.unreachable
|
|
||||||
func Unreachable()
|
|
||||||
|
|
||||||
//go:linkname Malloc C.malloc
|
//go:linkname Malloc C.malloc
|
||||||
func Malloc(size uintptr) Pointer
|
func Malloc(size uintptr) Pointer
|
||||||
|
|
||||||
|
//go:linkname Free C.free
|
||||||
|
func Free(ptr Pointer)
|
||||||
|
|
||||||
//go:linkname Memcpy C.memcpy
|
//go:linkname Memcpy C.memcpy
|
||||||
func Memcpy(dst, src Pointer, n uintptr) Pointer
|
func Memcpy(dst, src Pointer, n uintptr) Pointer
|
||||||
|
|
||||||
@@ -71,8 +76,17 @@ func GoStringData(string) *Char
|
|||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
//go:linkname Remove C.remove
|
//go:linkname AllocaSigjmpBuf llgo.sigjmpbuf
|
||||||
func Remove(path *Char) Int
|
func AllocaSigjmpBuf() Pointer
|
||||||
|
|
||||||
|
//go:linkname Sigsetjmp llgo.sigsetjmp
|
||||||
|
func Sigsetjmp(jb Pointer, savemask Int) Int
|
||||||
|
|
||||||
|
//go:linkname Siglongjmp llgo.siglongjmp
|
||||||
|
func Siglongjmp(jb Pointer, retval Int)
|
||||||
|
|
||||||
|
//go:linkname Unreachable llgo.unreachable
|
||||||
|
func Unreachable()
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
@@ -89,26 +103,37 @@ func Qsort(base Pointer, count, elem uintptr, compar func(a, b Pointer) Int)
|
|||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
//go:linkname Stdin __stdinp
|
|
||||||
var Stdin FilePtr
|
|
||||||
|
|
||||||
//go:linkname Stdout __stdoutp
|
|
||||||
var Stdout FilePtr
|
|
||||||
|
|
||||||
//go:linkname Stderr __stderrp
|
|
||||||
var Stderr FilePtr
|
|
||||||
|
|
||||||
//go:linkname Printf C.printf
|
//go:linkname Printf C.printf
|
||||||
func Printf(format *Char, __llgo_va_list ...any) Int
|
func Printf(format *Char, __llgo_va_list ...any) Int
|
||||||
|
|
||||||
//go:linkname Fprintf C.fprintf
|
//go:linkname Fprintf C.fprintf
|
||||||
func Fprintf(fp FilePtr, format *Char, __llgo_va_list ...any) Int
|
func Fprintf(fp FilePtr, format *Char, __llgo_va_list ...any) Int
|
||||||
|
|
||||||
|
//go:linkname Fwrite C.fwrite
|
||||||
|
func Fwrite(data Pointer, size, count uintptr, fp FilePtr) uintptr
|
||||||
|
|
||||||
|
//go:linkname Fputc C.fputc
|
||||||
|
func Fputc(c Int, fp FilePtr) Int
|
||||||
|
|
||||||
|
//go:linkname Fputs C.fputs
|
||||||
|
func Fputs(s *Char, fp FilePtr) Int
|
||||||
|
|
||||||
|
//go:linkname Fflush C.fflush
|
||||||
|
func Fflush(fp FilePtr) Int
|
||||||
|
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
//go:linkname Remove C.remove
|
||||||
|
func Remove(path *Char) Int
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
//go:linkname Time C.time
|
//go:linkname Time C.time
|
||||||
func Time(*int32) int32
|
func Time(*int32) int32
|
||||||
|
|
||||||
|
//go:linkname Usleep C.usleep
|
||||||
|
func Usleep(useconds Uint) Int
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
type Option struct {
|
type Option struct {
|
||||||
@@ -146,3 +171,6 @@ func GetoptLong(argc Int, argv **Char, optstring *Char, longopts *Option, longin
|
|||||||
func GetoptLongOnly(argc Int, argv **Char, optstring *Char, longopts *Option, longindex *Int) Int
|
func GetoptLongOnly(argc Int, argv **Char, optstring *Char, longopts *Option, longindex *Int) Int
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
//go:linkname Atoi C.atoi
|
||||||
|
func Atoi(s *Char) Int
|
||||||
|
|||||||
31
c/c_default.go
Normal file
31
c/c_default.go
Normal file
@@ -0,0 +1,31 @@
|
|||||||
|
//go:build !linux
|
||||||
|
// +build !linux
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2024 The GoPlus Authors (goplus.org). All rights reserved.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package c
|
||||||
|
|
||||||
|
import _ "unsafe"
|
||||||
|
|
||||||
|
//go:linkname Stdin __stdinp
|
||||||
|
var Stdin FilePtr
|
||||||
|
|
||||||
|
//go:linkname Stdout __stdoutp
|
||||||
|
var Stdout FilePtr
|
||||||
|
|
||||||
|
//go:linkname Stderr __stderrp
|
||||||
|
var Stderr FilePtr
|
||||||
31
c/c_linux.go
Normal file
31
c/c_linux.go
Normal file
@@ -0,0 +1,31 @@
|
|||||||
|
//go:build linux
|
||||||
|
// +build linux
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2024 The GoPlus Authors (goplus.org). All rights reserved.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package c
|
||||||
|
|
||||||
|
import _ "unsafe"
|
||||||
|
|
||||||
|
//go:linkname Stdin stdin
|
||||||
|
var Stdin FilePtr
|
||||||
|
|
||||||
|
//go:linkname Stdout stdout
|
||||||
|
var Stdout FilePtr
|
||||||
|
|
||||||
|
//go:linkname Stderr stderr
|
||||||
|
var Stderr FilePtr
|
||||||
35
c/cjson/README.md
Normal file
35
c/cjson/README.md
Normal file
@@ -0,0 +1,35 @@
|
|||||||
|
LLGo wrapper of DaveGamble/cJSON
|
||||||
|
=====
|
||||||
|
[](https://github.com/goplus/cjson/actions/workflows/go.yml)
|
||||||
|
[](https://github.com/goplus/cjson/releases)
|
||||||
|
[](https://pkg.go.dev/github.com/goplus/cjson)
|
||||||
|
[](https://github.com/goplus/llgo)
|
||||||
|
[](https://github.com/goplus/gop)
|
||||||
|
|
||||||
|
## How to install
|
||||||
|
|
||||||
|
```sh
|
||||||
|
git clone https://github.com/goplus/cjson.git
|
||||||
|
cd cjson
|
||||||
|
git submodule init
|
||||||
|
git submodule update
|
||||||
|
mkdir build.dir
|
||||||
|
cd build.dir
|
||||||
|
cmake ../cJSON
|
||||||
|
sudo make install
|
||||||
|
```
|
||||||
|
|
||||||
|
## Demos
|
||||||
|
|
||||||
|
The `_demo` directory contains our demos (it start with `_` to prevent the `go` command from compiling it):
|
||||||
|
|
||||||
|
* [mkjson](_demo/mkjson/mkjson.go): create a json object and print it
|
||||||
|
|
||||||
|
### How to run demos
|
||||||
|
|
||||||
|
To run the demos in directory `_demo`:
|
||||||
|
|
||||||
|
```sh
|
||||||
|
cd <demo-directory> # eg. cd _demo/mkjson
|
||||||
|
llgo run .
|
||||||
|
```
|
||||||
27
c/cjson/_demo/mkjson/mkjson.go
Normal file
27
c/cjson/_demo/mkjson/mkjson.go
Normal file
@@ -0,0 +1,27 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/goplus/llgo/c"
|
||||||
|
"github.com/goplus/llgo/c/cjson"
|
||||||
|
)
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
mod := cjson.Object()
|
||||||
|
mod.SetItem(c.Str("name"), cjson.String(c.Str("math")))
|
||||||
|
|
||||||
|
syms := cjson.Array()
|
||||||
|
|
||||||
|
fn := cjson.Object()
|
||||||
|
fn.SetItem(c.Str("name"), cjson.String(c.Str("sqrt")))
|
||||||
|
fn.SetItem(c.Str("sig"), cjson.String(c.Str("(x, /)")))
|
||||||
|
syms.AddItem(fn)
|
||||||
|
|
||||||
|
v := cjson.Object()
|
||||||
|
v.SetItem(c.Str("name"), cjson.String(c.Str("pi")))
|
||||||
|
syms.AddItem(v)
|
||||||
|
|
||||||
|
mod.SetItem(c.Str("items"), syms)
|
||||||
|
|
||||||
|
c.Printf(c.Str("%s\n"), mod.CStr())
|
||||||
|
mod.Delete()
|
||||||
|
}
|
||||||
121
c/cjson/cjson.go
Normal file
121
c/cjson/cjson.go
Normal file
@@ -0,0 +1,121 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2024 The GoPlus Authors (goplus.org). All rights reserved.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package cjson
|
||||||
|
|
||||||
|
import (
|
||||||
|
_ "unsafe"
|
||||||
|
|
||||||
|
"github.com/goplus/llgo/c"
|
||||||
|
)
|
||||||
|
|
||||||
|
const (
|
||||||
|
LLGoPackage = "link: cjson"
|
||||||
|
)
|
||||||
|
|
||||||
|
// llgo:type C
|
||||||
|
type JSON struct {
|
||||||
|
Unused [0]byte
|
||||||
|
}
|
||||||
|
|
||||||
|
//go:linkname Null C.cJSON_CreateNull
|
||||||
|
func Null() *JSON
|
||||||
|
|
||||||
|
//go:linkname True C.cJSON_CreateTrue
|
||||||
|
func True() *JSON
|
||||||
|
|
||||||
|
//go:linkname False C.cJSON_CreateFalse
|
||||||
|
func False() *JSON
|
||||||
|
|
||||||
|
//go:linkname Bool C.cJSON_CreateBool
|
||||||
|
func Bool(boolean c.Int) *JSON
|
||||||
|
|
||||||
|
//go:linkname Number C.cJSON_CreateNumber
|
||||||
|
func Number(num float64) *JSON
|
||||||
|
|
||||||
|
//go:linkname String C.cJSON_CreateString
|
||||||
|
func String(str *c.Char) *JSON
|
||||||
|
|
||||||
|
//go:linkname Array C.cJSON_CreateArray
|
||||||
|
func Array() *JSON
|
||||||
|
|
||||||
|
//go:linkname Object C.cJSON_CreateObject
|
||||||
|
func Object() *JSON
|
||||||
|
|
||||||
|
// raw json
|
||||||
|
//
|
||||||
|
//go:linkname Raw C.cJSON_CreateRaw
|
||||||
|
func Raw(raw *c.Char) *JSON
|
||||||
|
|
||||||
|
// Create a string where valuestring references a string so
|
||||||
|
// it will not be freed by Delete
|
||||||
|
//
|
||||||
|
//go:linkname StringRef C.cJSON_CreateStringReference
|
||||||
|
func StringRef(str *c.Char) *JSON
|
||||||
|
|
||||||
|
// Create an object that only references it's elements so
|
||||||
|
// they will not be freed by Delete
|
||||||
|
//
|
||||||
|
//go:linkname ObjectRef C.cJSON_CreateObjectReference
|
||||||
|
func ObjectRef(child *JSON) *JSON
|
||||||
|
|
||||||
|
// Create an array that only references it's elements so
|
||||||
|
// they will not be freed by Delete
|
||||||
|
//
|
||||||
|
//go:linkname ArrayRef C.cJSON_CreateArrayReference
|
||||||
|
func ArrayRef(child *JSON) *JSON
|
||||||
|
|
||||||
|
// Delete a JSON entity and all subentities.
|
||||||
|
//
|
||||||
|
// llgo:link (*JSON).Delete C.cJSON_Delete
|
||||||
|
func (o *JSON) Delete() {}
|
||||||
|
|
||||||
|
// Append item to the specified array.
|
||||||
|
//
|
||||||
|
// llgo:link (*JSON).AddItem C.cJSON_AddItemToArray
|
||||||
|
func (o *JSON) AddItem(item *JSON) c.Int { return 0 }
|
||||||
|
|
||||||
|
// Append item to the specified object.
|
||||||
|
//
|
||||||
|
// llgo:link (*JSON).SetItem C.cJSON_AddItemToObject
|
||||||
|
func (o *JSON) SetItem(key *c.Char, item *JSON) c.Int { return 0 }
|
||||||
|
|
||||||
|
// llgo:link (*JSON).CStr C.cJSON_PrintUnformatted
|
||||||
|
func (o *JSON) CStr() *c.Char { return nil }
|
||||||
|
|
||||||
|
// Same as CStr. Provided for Go+.
|
||||||
|
//
|
||||||
|
// llgo:link (*JSON).Cstr C.cJSON_PrintUnformatted
|
||||||
|
func (o *JSON) Cstr() *c.Char { return nil }
|
||||||
|
|
||||||
|
// Render a JSON entity to text for transfer/storage.
|
||||||
|
//
|
||||||
|
// llgo:link (*JSON).Print C.cJSON_Print
|
||||||
|
func (o *JSON) Print() *c.Char { return nil }
|
||||||
|
|
||||||
|
// Render a JSON entity to text for transfer/storage without any formatting.
|
||||||
|
//
|
||||||
|
// llgo:link (*JSON).PrintUnformatted C.cJSON_PrintUnformatted
|
||||||
|
func (o *JSON) PrintUnformatted() *c.Char { return nil }
|
||||||
|
|
||||||
|
// Render a JSON entity to text using a buffered strategy.
|
||||||
|
//
|
||||||
|
// prebuffer is a guess at the final size. guessing well reduces reallocation.
|
||||||
|
//
|
||||||
|
// fmt=0 gives unformatted, =1 gives formatted.
|
||||||
|
//
|
||||||
|
// llgo:link (*JSON).PrintBuffered C.cJSON_PrintBuffered
|
||||||
|
func (o *JSON) PrintBuffered(prebuffer c.Int, fmt c.Int) *c.Char { return nil }
|
||||||
BIN
c/cjson/llgo_autogen.lla
Normal file
BIN
c/cjson/llgo_autogen.lla
Normal file
Binary file not shown.
159
c/llama2/llama2.go
Normal file
159
c/llama2/llama2.go
Normal file
@@ -0,0 +1,159 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2024 The GoPlus Authors (goplus.org). All rights reserved.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package llama2
|
||||||
|
|
||||||
|
import (
|
||||||
|
_ "unsafe"
|
||||||
|
|
||||||
|
"github.com/goplus/llgo/c"
|
||||||
|
)
|
||||||
|
|
||||||
|
const (
|
||||||
|
LLGoPackage = "link"
|
||||||
|
)
|
||||||
|
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
// llgo:type C
|
||||||
|
type TokenIndex struct {
|
||||||
|
Str *c.Char
|
||||||
|
Id c.Int
|
||||||
|
}
|
||||||
|
|
||||||
|
// llgo:type C
|
||||||
|
type Tokenizer struct {
|
||||||
|
Vocab **c.Char
|
||||||
|
VocabScores *c.Float
|
||||||
|
SortedVocab *TokenIndex
|
||||||
|
VocabSize c.Int
|
||||||
|
MaxTokenLength c.Uint
|
||||||
|
BytePieces [512]uint8 // stores all single-byte strings
|
||||||
|
}
|
||||||
|
|
||||||
|
//go:linkname BuildTokenizer C.build_tokenizer
|
||||||
|
func BuildTokenizer(t *Tokenizer, tokenizerPath *c.Char, vocabSize c.Int)
|
||||||
|
|
||||||
|
//go:linkname FreeTokenizer C.free_tokenizer
|
||||||
|
func FreeTokenizer(t *Tokenizer)
|
||||||
|
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
// llgo:type C
|
||||||
|
type Config struct {
|
||||||
|
Dim c.Int // transformer dimension
|
||||||
|
HiddenDim c.Int // for ffn layers
|
||||||
|
NLayers c.Int // number of layers
|
||||||
|
NHeads c.Int // number of query heads
|
||||||
|
NKVHeads c.Int // number of key/value heads (can be < query heads because of multiquery)
|
||||||
|
VocabSize c.Int // vocabulary size, usually 256 (byte-level)
|
||||||
|
SeqLen c.Int // max sequence length
|
||||||
|
}
|
||||||
|
|
||||||
|
// llgo:type C
|
||||||
|
type TransformerWeights struct {
|
||||||
|
// token embedding table
|
||||||
|
TokenEmbeddingTable *c.Float // (vocab_size, dim)
|
||||||
|
// weights for rmsnorms
|
||||||
|
RmsAttWeight *c.Float // (layer, dim) rmsnorm weights
|
||||||
|
RmsFfnWeight *c.Float // (layer, dim)
|
||||||
|
// weights for matmuls. note dim == n_heads * head_size
|
||||||
|
Wq *c.Float // (layer, dim, n_heads * head_size)
|
||||||
|
Wk *c.Float // (layer, dim, n_kv_heads * head_size)
|
||||||
|
Wv *c.Float // (layer, dim, n_kv_heads * head_size)
|
||||||
|
Wo *c.Float // (layer, n_heads * head_size, dim)
|
||||||
|
// weights for ffn
|
||||||
|
W1 *c.Float // (layer, hidden_dim, dim)
|
||||||
|
W2 *c.Float // (layer, dim, hidden_dim)
|
||||||
|
W3 *c.Float // (layer, hidden_dim, dim)
|
||||||
|
// final rmsnorm
|
||||||
|
RmsFinalWeight *c.Float // (dim,)
|
||||||
|
// (optional) classifier weights for the logits, on the last layer
|
||||||
|
Wcls *c.Float
|
||||||
|
}
|
||||||
|
|
||||||
|
// llgo:type C
|
||||||
|
type RunState struct {
|
||||||
|
// current wave of activations
|
||||||
|
X *c.Float // activation at current time stamp (dim,)
|
||||||
|
Xb *c.Float // same, but inside a residual branch (dim,)
|
||||||
|
Xb2 *c.Float // an additional buffer just for convenience (dim,)
|
||||||
|
Hb *c.Float // buffer for hidden dimension in the ffn (hidden_dim,)
|
||||||
|
Hb2 *c.Float // buffer for hidden dimension in the ffn (hidden_dim,)
|
||||||
|
Q *c.Float // query (dim,)
|
||||||
|
K *c.Float // key (dim,)
|
||||||
|
V *c.Float // value (dim,)
|
||||||
|
Att *c.Float // buffer for scores/attention values (n_heads, seq_len)
|
||||||
|
Logits *c.Float // output logits
|
||||||
|
// kv cache
|
||||||
|
KeyCache *c.Float // (layer, seq_len, dim)
|
||||||
|
ValueCache *c.Float // (layer, seq_len, dim)
|
||||||
|
}
|
||||||
|
|
||||||
|
// llgo:type C
|
||||||
|
type Transformer struct {
|
||||||
|
Config Config // the hyperparameters of the architecture (the blueprint)
|
||||||
|
Weights TransformerWeights // the weights of the model
|
||||||
|
State RunState // buffers for the "wave" of activations in the forward pass
|
||||||
|
|
||||||
|
// some more state needed to properly clean up the memory mapping (sigh)
|
||||||
|
Fd c.Int // file descriptor for memory mapping
|
||||||
|
Data *c.Float // memory mapped data pointer
|
||||||
|
FileSize uintptr // size of the checkpoint file in bytes
|
||||||
|
}
|
||||||
|
|
||||||
|
//go:linkname BuildTransformer C.build_transformer
|
||||||
|
func BuildTransformer(t *Transformer, checkpointPath *c.Char)
|
||||||
|
|
||||||
|
//go:linkname FreeTransformer C.free_transformer
|
||||||
|
func FreeTransformer(t *Transformer)
|
||||||
|
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
// llgo:type C
|
||||||
|
type ProbIndex struct {
|
||||||
|
Prob c.Float
|
||||||
|
Index c.Int
|
||||||
|
} // struct used when sorting probabilities during top-p sampling
|
||||||
|
|
||||||
|
// llgo:type C
|
||||||
|
type Sampler struct {
|
||||||
|
VocabSize c.Int
|
||||||
|
Probindex *ProbIndex // buffer used in top-p sampling
|
||||||
|
Temperature c.Float
|
||||||
|
Topp c.Float
|
||||||
|
RngState uint64
|
||||||
|
}
|
||||||
|
|
||||||
|
//go:linkname BuildSampler C.build_sampler
|
||||||
|
func BuildSampler(sampler *Sampler, vocabSize c.Int, temperature c.Float, topp c.Float, rngSeed uint64)
|
||||||
|
|
||||||
|
//go:linkname FreeSampler C.free_sampler
|
||||||
|
func FreeSampler(sampler *Sampler)
|
||||||
|
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
//go:linkname Generate C.generate
|
||||||
|
func Generate(
|
||||||
|
transformer *Transformer, tokenizer *Tokenizer, sampler *Sampler,
|
||||||
|
prompt *c.Char, steps c.Int)
|
||||||
|
|
||||||
|
//go:linkname Chat C.chat
|
||||||
|
func Chat(
|
||||||
|
transformer *Transformer, tokenizer *Tokenizer, sampler *Sampler,
|
||||||
|
cliUserPrompt *c.Char, cliSystemPrompt *c.Char, steps c.Int)
|
||||||
|
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"cl": [
|
"cl": [
|
||||||
"clang -emit-llvm -S -o llgo_autogen.ll -c llama2/run.c",
|
"clang -emit-llvm -S -o llgo_autogen.ll -c llama2/run.c",
|
||||||
"zip llgo_autogen.lla llgo_autogen.ll"
|
"rm llgo_autogen.lla; zip llgo_autogen.lla llgo_autogen.ll"
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
160
c/pthread/pthread.go
Normal file
160
c/pthread/pthread.go
Normal file
@@ -0,0 +1,160 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2024 The GoPlus Authors (goplus.org). All rights reserved.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package pthread
|
||||||
|
|
||||||
|
import (
|
||||||
|
_ "unsafe"
|
||||||
|
|
||||||
|
"github.com/goplus/llgo/c"
|
||||||
|
)
|
||||||
|
|
||||||
|
const (
|
||||||
|
LLGoPackage = "decl"
|
||||||
|
)
|
||||||
|
|
||||||
|
func __noop__() c.Int {
|
||||||
|
return 0
|
||||||
|
}
|
||||||
|
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
type aThread struct {
|
||||||
|
Unused [8]byte
|
||||||
|
}
|
||||||
|
|
||||||
|
// Thread represents a POSIX thread.
|
||||||
|
type Thread = *aThread
|
||||||
|
|
||||||
|
// The pthread_create() function starts a new thread in the calling
|
||||||
|
// process. The new thread starts execution by invoking
|
||||||
|
// start_routine(); arg is passed as the sole argument of
|
||||||
|
// start_routine().
|
||||||
|
//
|
||||||
|
// The new thread terminates in one of the following ways:
|
||||||
|
//
|
||||||
|
// - It calls pthread_exit(3), specifying an exit status value that
|
||||||
|
// is available to another thread in the same process that calls
|
||||||
|
// pthread_join(3).
|
||||||
|
//
|
||||||
|
// - It returns from start_routine(). This is equivalent to
|
||||||
|
// calling pthread_exit(3) with the value supplied in the return
|
||||||
|
// statement.
|
||||||
|
//
|
||||||
|
// - It is canceled (see pthread_cancel(3)).
|
||||||
|
//
|
||||||
|
// - Any of the threads in the process calls exit(3), or the main
|
||||||
|
// thread performs a return from main(). This causes the
|
||||||
|
// termination of all threads in the process.
|
||||||
|
//
|
||||||
|
// On success, pthread_create() returns 0; on error, it returns an
|
||||||
|
// error number, and the contents of *thread are undefined.
|
||||||
|
//
|
||||||
|
// See https://man7.org/linux/man-pages/man3/pthread_create.3.html
|
||||||
|
//
|
||||||
|
//go:linkname Create C.pthread_create
|
||||||
|
func Create(pthread *Thread, attr *Attr, routine func(c.Pointer) c.Pointer, arg c.Pointer) c.Int
|
||||||
|
|
||||||
|
// The pthread_join() function waits for the thread specified by
|
||||||
|
// thread to terminate. If that thread has already terminated, then
|
||||||
|
// pthread_join() returns immediately. The thread specified by
|
||||||
|
// thread must be joinable.
|
||||||
|
//
|
||||||
|
// If retval is not NULL, then pthread_join() copies the exit status
|
||||||
|
// of the target thread (i.e., the value that the target thread
|
||||||
|
// supplied to pthread_exit(3)) into the location pointed to by
|
||||||
|
// retval. If the target thread was canceled, then PTHREAD_CANCELED
|
||||||
|
// is placed in the location pointed to by retval.
|
||||||
|
//
|
||||||
|
// If multiple threads simultaneously try to join with the same
|
||||||
|
// thread, the results are undefined. If the thread calling
|
||||||
|
// pthread_join() is canceled, then the target thread will remain
|
||||||
|
// joinable (i.e., it will not be detached).
|
||||||
|
//
|
||||||
|
// See https://man7.org/linux/man-pages/man3/pthread_join.3.html
|
||||||
|
//
|
||||||
|
//go:linkname Join C.pthread_join
|
||||||
|
func Join(thread Thread, retval *c.Pointer) c.Int
|
||||||
|
|
||||||
|
// The pthread_exit() function terminates the calling thread and
|
||||||
|
// returns a value via retval that (if the thread is joinable) is
|
||||||
|
// available to another thread in the same process that calls
|
||||||
|
// pthread_join(3).
|
||||||
|
//
|
||||||
|
// See https://man7.org/linux/man-pages/man3/pthread_exit.3.html
|
||||||
|
//
|
||||||
|
//go:linkname Exit C.pthread_exit
|
||||||
|
func Exit(retval c.Pointer)
|
||||||
|
|
||||||
|
// The pthread_cancel() function sends a cancelation request to the
|
||||||
|
// thread thread.
|
||||||
|
//
|
||||||
|
// See https://man7.org/linux/man-pages/man3/pthread_cancel.3.html
|
||||||
|
//
|
||||||
|
//go:linkname Cancel C.pthread_cancel
|
||||||
|
func Cancel(thread Thread) c.Int
|
||||||
|
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
// Attr represents a POSIX thread attributes.
|
||||||
|
type Attr struct {
|
||||||
|
Detached byte
|
||||||
|
SsSp *c.Char
|
||||||
|
SsSize uintptr
|
||||||
|
}
|
||||||
|
|
||||||
|
// llgo:link (*Attr).Init C.pthread_attr_init
|
||||||
|
func (attr *Attr) Init() c.Int { return 0 }
|
||||||
|
|
||||||
|
// llgo:link (*Attr).Destroy C.pthread_attr_destroy
|
||||||
|
func (attr *Attr) Destroy() c.Int { return 0 }
|
||||||
|
|
||||||
|
// llgo:link (*Attr).GetDetached C.pthread_attr_getdetachstate
|
||||||
|
func (attr *Attr) GetDetached(detached *c.Int) c.Int { return 0 }
|
||||||
|
|
||||||
|
// llgo:link (*Attr).SetDetached C.pthread_attr_setdetachstate
|
||||||
|
func (attr *Attr) SetDetached(detached c.Int) c.Int { return 0 }
|
||||||
|
|
||||||
|
// llgo:link (*Attr).GetStackSize C.pthread_attr_getstacksize
|
||||||
|
func (attr *Attr) GetStackSize(stackSize *uintptr) c.Int { return 0 }
|
||||||
|
|
||||||
|
// llgo:link (*Attr).SetStackSize C.pthread_attr_setstacksize
|
||||||
|
func (attr *Attr) SetStackSize(stackSize uintptr) c.Int { return 0 }
|
||||||
|
|
||||||
|
// llgo:link (*Attr).GetStackAddr C.pthread_attr_getstackaddr
|
||||||
|
func (attr *Attr) GetStackAddr(stackAddr *c.Pointer) c.Int { return 0 }
|
||||||
|
|
||||||
|
// llgo:link (*Attr).SetStackAddr C.pthread_attr_setstackaddr
|
||||||
|
func (attr *Attr) SetStackAddr(stackAddr c.Pointer) c.Int { return 0 }
|
||||||
|
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
|
// Thread Local Storage
|
||||||
|
|
||||||
|
type Key c.Uint
|
||||||
|
|
||||||
|
// llgo:link (*Key).Create C.pthread_key_create
|
||||||
|
func (key *Key) Create(destructor func(c.Pointer)) c.Int { return 0 }
|
||||||
|
|
||||||
|
// llgo:link Key.Delete C.pthread_key_delete
|
||||||
|
func (key Key) Delete() c.Int { return 0 }
|
||||||
|
|
||||||
|
// llgo:link Key.Get C.pthread_getspecific
|
||||||
|
func (key Key) Get() c.Pointer { return nil }
|
||||||
|
|
||||||
|
// llgo:link Key.Set C.pthread_setspecific
|
||||||
|
func (key Key) Set(value c.Pointer) c.Int { return __noop__() }
|
||||||
|
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
53
c/setjmp/setjmp.go
Normal file
53
c/setjmp/setjmp.go
Normal file
@@ -0,0 +1,53 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2024 The GoPlus Authors (goplus.org). All rights reserved.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package setjmp
|
||||||
|
|
||||||
|
// #include <setjmp.h>
|
||||||
|
import "C"
|
||||||
|
|
||||||
|
import (
|
||||||
|
_ "unsafe"
|
||||||
|
|
||||||
|
"github.com/goplus/llgo/c"
|
||||||
|
)
|
||||||
|
|
||||||
|
const (
|
||||||
|
LLGoPackage = "decl"
|
||||||
|
)
|
||||||
|
|
||||||
|
type (
|
||||||
|
JmpBuf = C.jmp_buf
|
||||||
|
SigjmpBuf = C.sigjmp_buf
|
||||||
|
)
|
||||||
|
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
//go:linkname Setjmp C.setjmp
|
||||||
|
func Setjmp(env *JmpBuf) c.Int
|
||||||
|
|
||||||
|
//go:linkname Longjmp C.longjmp
|
||||||
|
func Longjmp(env *JmpBuf, val c.Int)
|
||||||
|
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
//go:linkname Sigsetjmp C.sigsetjmp
|
||||||
|
func Sigsetjmp(env *SigjmpBuf, savemask c.Int) c.Int
|
||||||
|
|
||||||
|
//go:linkname Siglongjmp C.siglongjmp
|
||||||
|
func Siglongjmp(env *SigjmpBuf, val c.Int)
|
||||||
|
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
5
c/setjmp/trycatch/_code/demo.cpp
Normal file
5
c/setjmp/trycatch/_code/demo.cpp
Normal file
@@ -0,0 +1,5 @@
|
|||||||
|
#include <stdexcept>
|
||||||
|
|
||||||
|
extern "C" void throwCppException() {
|
||||||
|
throw std::runtime_error("C++ exception");
|
||||||
|
}
|
||||||
13
c/setjmp/trycatch/_code/try_catch.cpp
Normal file
13
c/setjmp/trycatch/_code/try_catch.cpp
Normal file
@@ -0,0 +1,13 @@
|
|||||||
|
#include <exception>
|
||||||
|
#include <stdio.h>
|
||||||
|
|
||||||
|
extern "C" void throwCppException();
|
||||||
|
|
||||||
|
int main() {
|
||||||
|
try {
|
||||||
|
throwCppException();
|
||||||
|
} catch (std::exception& e) {
|
||||||
|
printf("Hi, %s\n", e.what());
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
28
c/setjmp/trycatch/demo.go
Normal file
28
c/setjmp/trycatch/demo.go
Normal file
@@ -0,0 +1,28 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2024 The GoPlus Authors (goplus.org). All rights reserved.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package trycatch
|
||||||
|
|
||||||
|
import (
|
||||||
|
_ "unsafe"
|
||||||
|
)
|
||||||
|
|
||||||
|
const (
|
||||||
|
LLGoPackage = "link: c++"
|
||||||
|
)
|
||||||
|
|
||||||
|
//go:linkname ThrowCppException C.throwCppException
|
||||||
|
func ThrowCppException()
|
||||||
8
c/setjmp/trycatch/llgo.cfg
Normal file
8
c/setjmp/trycatch/llgo.cfg
Normal file
@@ -0,0 +1,8 @@
|
|||||||
|
{
|
||||||
|
"cl": [
|
||||||
|
"clang -emit-llvm -S -o demo.ll -c _code/demo.cpp",
|
||||||
|
"clang -emit-llvm -S -o _code/llgo_autogen.ll -c _code/try_catch.cpp",
|
||||||
|
"llgen .",
|
||||||
|
"rm llgo_autogen.lla; zip llgo_autogen.lla llgo_autogen.ll demo.ll",
|
||||||
|
]
|
||||||
|
}
|
||||||
BIN
c/setjmp/trycatch/llgo_autogen.lla
Normal file
BIN
c/setjmp/trycatch/llgo_autogen.lla
Normal file
Binary file not shown.
35
c/sqlite/README.md
Normal file
35
c/sqlite/README.md
Normal file
@@ -0,0 +1,35 @@
|
|||||||
|
LLGo wrapper of sqlite
|
||||||
|
=====
|
||||||
|
[](https://github.com/goplus/sqlite/actions/workflows/go.yml)
|
||||||
|
[](https://github.com/goplus/sqlite/releases)
|
||||||
|
[](https://pkg.go.dev/github.com/goplus/sqlite)
|
||||||
|
[](https://github.com/goplus/llgo)
|
||||||
|
[](https://github.com/goplus/gop)
|
||||||
|
|
||||||
|
## How to install
|
||||||
|
|
||||||
|
```sh
|
||||||
|
git clone https://github.com/goplus/sqlite.git
|
||||||
|
cd sqlite
|
||||||
|
git submodule init
|
||||||
|
git submodule update
|
||||||
|
mkdir build.dir
|
||||||
|
cd build.dir
|
||||||
|
../sqlite/configure --enable-shared
|
||||||
|
sudo make install
|
||||||
|
```
|
||||||
|
|
||||||
|
## Demos
|
||||||
|
|
||||||
|
The `_demo` directory contains our demos (it start with `_` to prevent the `go` command from compiling it):
|
||||||
|
|
||||||
|
* [sqlitedemo](_demo/sqlitedemo/demo.go): a basic sqlite demo
|
||||||
|
|
||||||
|
### How to run demos
|
||||||
|
|
||||||
|
To run the demos in directory `_demo`:
|
||||||
|
|
||||||
|
```sh
|
||||||
|
cd <demo-directory> # eg. cd _demo/sqlitedemo
|
||||||
|
llgo run .
|
||||||
|
```
|
||||||
@@ -2,7 +2,7 @@ package main
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"github.com/goplus/llgo/c"
|
"github.com/goplus/llgo/c"
|
||||||
"github.com/goplus/llgo/x/sqlite"
|
"github.com/goplus/llgo/c/sqlite"
|
||||||
)
|
)
|
||||||
|
|
||||||
func main() {
|
func main() {
|
||||||
BIN
c/sqlite/llgo_autogen.lla
Normal file
BIN
c/sqlite/llgo_autogen.lla
Normal file
Binary file not shown.
@@ -22,27 +22,23 @@ import (
|
|||||||
"github.com/goplus/llgo/c"
|
"github.com/goplus/llgo/c"
|
||||||
)
|
)
|
||||||
|
|
||||||
type (
|
|
||||||
Char = c.Char
|
|
||||||
Int = c.Int
|
|
||||||
Pointer = c.Pointer
|
|
||||||
)
|
|
||||||
|
|
||||||
const (
|
const (
|
||||||
LLGoPackage = "link"
|
LLGoPackage = "link: sqlite3"
|
||||||
)
|
)
|
||||||
|
|
||||||
// llgo:type C
|
// llgo:type C
|
||||||
type Sqlite3 struct {
|
type Sqlite3 struct {
|
||||||
|
Unused [8]byte
|
||||||
}
|
}
|
||||||
|
|
||||||
// llgo:type C
|
// llgo:type C
|
||||||
type Stmt struct {
|
type Stmt struct {
|
||||||
|
Unused [8]byte
|
||||||
}
|
}
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
type Errno Int
|
type Errno c.Int
|
||||||
|
|
||||||
const (
|
const (
|
||||||
OK Errno = 0 // Successful result
|
OK Errno = 0 // Successful result
|
||||||
@@ -80,11 +76,11 @@ const (
|
|||||||
Done Errno = 101 // sqlite3_step() has finished executing
|
Done Errno = 101 // sqlite3_step() has finished executing
|
||||||
)
|
)
|
||||||
|
|
||||||
// llgo:link (Errno).Errstr C.sqlite3_errstr
|
// llgo:link Errno.Errstr C.sqlite3_errstr
|
||||||
func (err Errno) Errstr() *Char { return nil }
|
func (err Errno) Errstr() *c.Char { return nil }
|
||||||
|
|
||||||
// llgo:link (*Sqlite3).Errmsg C.sqlite3_errmsg
|
// llgo:link (*Sqlite3).Errmsg C.sqlite3_errmsg
|
||||||
func (db *Sqlite3) Errmsg() *Char { return nil }
|
func (db *Sqlite3) Errmsg() *c.Char { return nil }
|
||||||
|
|
||||||
// llgo:link (*Sqlite3).Errcode C.sqlite3_errcode
|
// llgo:link (*Sqlite3).Errcode C.sqlite3_errcode
|
||||||
func (db *Sqlite3) Errcode() Errno { return 0 }
|
func (db *Sqlite3) Errcode() Errno { return 0 }
|
||||||
@@ -95,13 +91,13 @@ func (db *Sqlite3) ExtendedErrcode() Errno { return 0 }
|
|||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
//go:linkname doOpen C.sqlite3_open
|
//go:linkname doOpen C.sqlite3_open
|
||||||
func doOpen(filename *Char, ppDb **Sqlite3) Errno
|
func doOpen(filename *c.Char, ppDb **Sqlite3) Errno
|
||||||
|
|
||||||
//go:linkname doOpenV2 C.sqlite3_open_v2
|
//go:linkname doOpenV2 C.sqlite3_open_v2
|
||||||
func doOpenV2(filename *Char, ppDb **Sqlite3, flags OpenFlags, zVfs *Char) Errno
|
func doOpenV2(filename *c.Char, ppDb **Sqlite3, flags OpenFlags, zVfs *c.Char) Errno
|
||||||
|
|
||||||
// OpenFlags represents SQLite open flags.
|
// OpenFlags represents SQLite open flags.
|
||||||
type OpenFlags Int
|
type OpenFlags c.Int
|
||||||
|
|
||||||
const (
|
const (
|
||||||
OpenReadOnly OpenFlags = 0x00000001
|
OpenReadOnly OpenFlags = 0x00000001
|
||||||
@@ -130,7 +126,7 @@ const (
|
|||||||
|
|
||||||
// Opening A New Database Connection
|
// Opening A New Database Connection
|
||||||
// filename: Database filename (UTF-8)
|
// filename: Database filename (UTF-8)
|
||||||
func Open(filename *Char) (db *Sqlite3, err Errno) {
|
func Open(filename *c.Char) (db *Sqlite3, err Errno) {
|
||||||
err = doOpen(filename, &db)
|
err = doOpen(filename, &db)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
@@ -138,7 +134,7 @@ func Open(filename *Char) (db *Sqlite3, err Errno) {
|
|||||||
// Opening A New Database Connection
|
// Opening A New Database Connection
|
||||||
// filename: Database filename (UTF-8)
|
// filename: Database filename (UTF-8)
|
||||||
// zVfs: Name of VFS module to use
|
// zVfs: Name of VFS module to use
|
||||||
func OpenV2(filename *Char, flags OpenFlags, zVfs *Char) (db *Sqlite3, err Errno) {
|
func OpenV2(filename *c.Char, flags OpenFlags, zVfs *c.Char) (db *Sqlite3, err Errno) {
|
||||||
err = doOpenV2(filename, &db, flags, zVfs)
|
err = doOpenV2(filename, &db, flags, zVfs)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
@@ -156,22 +152,22 @@ func (db *Sqlite3) CloseV2() Errno { return 0 }
|
|||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
// llgo:link (*Sqlite3).doPrepare C.sqlite3_prepare
|
// llgo:link (*Sqlite3).doPrepare C.sqlite3_prepare
|
||||||
func (*Sqlite3) doPrepare(*Char, Int, **Stmt, **Char) Errno {
|
func (*Sqlite3) doPrepare(*c.Char, c.Int, **Stmt, **c.Char) Errno {
|
||||||
return 0
|
return 0
|
||||||
}
|
}
|
||||||
|
|
||||||
// llgo:link (*Sqlite3).doPrepareV2 C.sqlite3_prepare_v2
|
// llgo:link (*Sqlite3).doPrepareV2 C.sqlite3_prepare_v2
|
||||||
func (*Sqlite3) doPrepareV2(*Char, Int, **Stmt, **Char) Errno {
|
func (*Sqlite3) doPrepareV2(*c.Char, c.Int, **Stmt, **c.Char) Errno {
|
||||||
return 0
|
return 0
|
||||||
}
|
}
|
||||||
|
|
||||||
// llgo:link (*Sqlite3).doPrepareV3 C.sqlite3_prepare_v3
|
// llgo:link (*Sqlite3).doPrepareV3 C.sqlite3_prepare_v3
|
||||||
func (*Sqlite3) doPrepareV3(*Char, Int, PrepareFlags, **Stmt, **Char) Errno {
|
func (*Sqlite3) doPrepareV3(*c.Char, c.Int, PrepareFlags, **Stmt, **c.Char) Errno {
|
||||||
return 0
|
return 0
|
||||||
}
|
}
|
||||||
|
|
||||||
// PrepareFlags represents SQLite prepare flags.
|
// PrepareFlags represents SQLite prepare flags.
|
||||||
type PrepareFlags Int
|
type PrepareFlags c.Int
|
||||||
|
|
||||||
const (
|
const (
|
||||||
PreparePersistent PrepareFlags = 0x01
|
PreparePersistent PrepareFlags = 0x01
|
||||||
@@ -181,17 +177,17 @@ const (
|
|||||||
|
|
||||||
// Compiling An SQL Statement
|
// Compiling An SQL Statement
|
||||||
// tail: Pointer to unused portion of sql
|
// tail: Pointer to unused portion of sql
|
||||||
func (db *Sqlite3) Prepare(sql string, tail **Char) (stmt *Stmt, err Errno) {
|
func (db *Sqlite3) Prepare(sql string, tail **c.Char) (stmt *Stmt, err Errno) {
|
||||||
err = db.doPrepare(c.GoStringData(sql), c.Int(len(sql)), &stmt, tail)
|
err = db.doPrepare(c.GoStringData(sql), c.Int(len(sql)), &stmt, tail)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func (db *Sqlite3) PrepareV2(sql string, tail **Char) (stmt *Stmt, err Errno) {
|
func (db *Sqlite3) PrepareV2(sql string, tail **c.Char) (stmt *Stmt, err Errno) {
|
||||||
err = db.doPrepareV2(c.GoStringData(sql), c.Int(len(sql)), &stmt, tail)
|
err = db.doPrepareV2(c.GoStringData(sql), c.Int(len(sql)), &stmt, tail)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func (db *Sqlite3) PrepareV3(sql string, flags PrepareFlags, tail **Char) (stmt *Stmt, err Errno) {
|
func (db *Sqlite3) PrepareV3(sql string, flags PrepareFlags, tail **c.Char) (stmt *Stmt, err Errno) {
|
||||||
err = db.doPrepareV3(c.GoStringData(sql), c.Int(len(sql)), flags, &stmt, tail)
|
err = db.doPrepareV3(c.GoStringData(sql), c.Int(len(sql)), flags, &stmt, tail)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
@@ -204,10 +200,10 @@ func (stmt *Stmt) Close() Errno { return 0 }
|
|||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
// llgo:link (*Stmt).BindInt C.sqlite3_bind_int
|
// llgo:link (*Stmt).BindInt C.sqlite3_bind_int
|
||||||
func (*Stmt) BindInt(idx Int, val Int) Errno { return 0 }
|
func (*Stmt) BindInt(idx c.Int, val c.Int) Errno { return 0 }
|
||||||
|
|
||||||
// llgo:link (*Stmt).BindInt64 C.sqlite3_bind_int64
|
// llgo:link (*Stmt).BindInt64 C.sqlite3_bind_int64
|
||||||
func (*Stmt) BindInt64(idx Int, val int64) Errno { return 0 }
|
func (*Stmt) BindInt64(idx c.Int, val int64) Errno { return 0 }
|
||||||
|
|
||||||
/*
|
/*
|
||||||
const (
|
const (
|
||||||
@@ -217,7 +213,9 @@ const (
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
// llgo:link (*Stmt).BindText C.sqlite3_bind_text
|
// llgo:link (*Stmt).BindText C.sqlite3_bind_text
|
||||||
func (*Stmt) BindText(idx Int, val *Char, nByte Int, destructor func(Pointer)) Errno { return 0 }
|
func (*Stmt) BindText(idx c.Int, val *c.Char, nByte c.Int, destructor func(c.Pointer)) Errno {
|
||||||
|
return 0
|
||||||
|
}
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
@@ -236,19 +234,19 @@ func (*Stmt) Step() Errno { return 0 }
|
|||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
// llgo:link (*Stmt).ColumnCount C.sqlite3_column_count
|
// llgo:link (*Stmt).ColumnCount C.sqlite3_column_count
|
||||||
func (stmt *Stmt) ColumnCount() Int { return 0 }
|
func (stmt *Stmt) ColumnCount() c.Int { return 0 }
|
||||||
|
|
||||||
// llgo:link (*Stmt).ColumnName C.sqlite3_column_name
|
// llgo:link (*Stmt).ColumnName C.sqlite3_column_name
|
||||||
func (stmt *Stmt) ColumnName(idx Int) *Char { return nil }
|
func (stmt *Stmt) ColumnName(idx c.Int) *c.Char { return nil }
|
||||||
|
|
||||||
// llgo:link (*Stmt).ColumnInt C.sqlite3_column_int
|
// llgo:link (*Stmt).ColumnInt C.sqlite3_column_int
|
||||||
func (stmt *Stmt) ColumnInt(idx Int) Int { return 0 }
|
func (stmt *Stmt) ColumnInt(idx c.Int) c.Int { return 0 }
|
||||||
|
|
||||||
// llgo:link (*Stmt).ColumnInt64 C.sqlite3_column_int64
|
// llgo:link (*Stmt).ColumnInt64 C.sqlite3_column_int64
|
||||||
func (stmt *Stmt) ColumnInt64(idx Int) int64 { return 0 }
|
func (stmt *Stmt) ColumnInt64(idx c.Int) int64 { return 0 }
|
||||||
|
|
||||||
// llgo:link (*Stmt).ColumnText C.sqlite3_column_text
|
// llgo:link (*Stmt).ColumnText C.sqlite3_column_text
|
||||||
func (stmt *Stmt) ColumnText(idx Int) *Char { return nil }
|
func (stmt *Stmt) ColumnText(idx c.Int) *c.Char { return nil }
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
@@ -256,8 +254,8 @@ func (stmt *Stmt) ColumnText(idx Int) *Char { return nil }
|
|||||||
//
|
//
|
||||||
// llgo:link (*Sqlite3).Exec C.sqlite3_exec
|
// llgo:link (*Sqlite3).Exec C.sqlite3_exec
|
||||||
func (*Sqlite3) Exec(
|
func (*Sqlite3) Exec(
|
||||||
sql *Char, callback func(arg Pointer, resultCols Int, colVals, colNames **Char) Int,
|
sql *c.Char, callback func(arg c.Pointer, resultCols c.Int, colVals, colNames **c.Char) c.Int,
|
||||||
arg Pointer, errmsg **Char) Errno {
|
arg c.Pointer, errmsg **c.Char) Errno {
|
||||||
return 0
|
return 0
|
||||||
}
|
}
|
||||||
|
|
||||||
60
chore/_xtool/pydump/pydump.go
Normal file
60
chore/_xtool/pydump/pydump.go
Normal file
@@ -0,0 +1,60 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2024 The GoPlus Authors (goplus.org). All rights reserved.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/goplus/llgo/c"
|
||||||
|
"github.com/goplus/llgo/c/cjson"
|
||||||
|
"github.com/goplus/llgo/py"
|
||||||
|
"github.com/goplus/llgo/py/inspect"
|
||||||
|
)
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
if c.Argc < 2 {
|
||||||
|
c.Fprintf(c.Stderr, c.Str("Usage: pydump <pythonLibPath>\n"))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
pyLib := c.Index(c.Argv, 1)
|
||||||
|
|
||||||
|
py.Initialize()
|
||||||
|
|
||||||
|
root := cjson.Object()
|
||||||
|
root.SetItem(c.Str("name"), cjson.String(pyLib))
|
||||||
|
|
||||||
|
items := cjson.Array()
|
||||||
|
mod := py.ImportModule(pyLib)
|
||||||
|
keys := mod.ModuleGetDict().DictKeys()
|
||||||
|
for i, n := uintptr(0), keys.ListLen(); i < n; i++ {
|
||||||
|
key := keys.ListItem(i)
|
||||||
|
val := mod.GetAttr(key)
|
||||||
|
doc := val.GetAttrString(c.Str("__doc__"))
|
||||||
|
sym := cjson.Object()
|
||||||
|
sym.SetItem(c.Str("type"), cjson.String(val.Type().TypeName().CStr()))
|
||||||
|
sym.SetItem(c.Str("name"), cjson.String(key.CStr()))
|
||||||
|
if doc != nil {
|
||||||
|
sym.SetItem(c.Str("doc"), cjson.String(doc.CStr()))
|
||||||
|
}
|
||||||
|
if val.Callable() != 0 {
|
||||||
|
sig := inspect.Signature(val)
|
||||||
|
sym.SetItem(c.Str("sig"), cjson.String(sig.Str().CStr()))
|
||||||
|
}
|
||||||
|
items.AddItem(sym)
|
||||||
|
}
|
||||||
|
root.SetItem(c.Str("items"), items)
|
||||||
|
|
||||||
|
c.Printf(c.Str("%s\n"), root.CStr())
|
||||||
|
}
|
||||||
@@ -22,6 +22,7 @@ import (
|
|||||||
"strings"
|
"strings"
|
||||||
|
|
||||||
"github.com/goplus/llgo/internal/llgen"
|
"github.com/goplus/llgo/internal/llgen"
|
||||||
|
"github.com/goplus/llgo/ssa"
|
||||||
"github.com/goplus/mod"
|
"github.com/goplus/mod"
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -29,10 +30,12 @@ func main() {
|
|||||||
dir, _, err := mod.FindGoMod(".")
|
dir, _, err := mod.FindGoMod(".")
|
||||||
check(err)
|
check(err)
|
||||||
|
|
||||||
|
ssa.Initialize(ssa.InitAll | ssa.InitNative)
|
||||||
llgen.Verbose = false
|
llgen.Verbose = false
|
||||||
|
|
||||||
llgenDir(dir + "/cl/_testlibc")
|
llgenDir(dir + "/cl/_testlibc")
|
||||||
llgenDir(dir + "/cl/_testrt")
|
llgenDir(dir + "/cl/_testrt")
|
||||||
|
llgenDir(dir + "/cl/_testgo")
|
||||||
llgenDir(dir+"/cl/_testpy", "")
|
llgenDir(dir+"/cl/_testpy", "")
|
||||||
llgenDir(dir+"/cl/_testdata", "")
|
llgenDir(dir+"/cl/_testdata", "")
|
||||||
}
|
}
|
||||||
|
|||||||
249
chore/llpyg/llpyg.go
Normal file
249
chore/llpyg/llpyg.go
Normal file
@@ -0,0 +1,249 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2024 The GoPlus Authors (goplus.org). All rights reserved.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"bytes"
|
||||||
|
"encoding/json"
|
||||||
|
"fmt"
|
||||||
|
"go/ast"
|
||||||
|
"go/token"
|
||||||
|
"go/types"
|
||||||
|
"log"
|
||||||
|
"os"
|
||||||
|
"os/exec"
|
||||||
|
"strings"
|
||||||
|
|
||||||
|
"github.com/goplus/gogen"
|
||||||
|
"github.com/goplus/llgo/chore/llpyg/pysig"
|
||||||
|
"github.com/goplus/llgo/ssa"
|
||||||
|
)
|
||||||
|
|
||||||
|
type symbol struct {
|
||||||
|
Name string `json:"name"`
|
||||||
|
Type string `json:"type"`
|
||||||
|
Doc string `json:"doc"`
|
||||||
|
Sig string `json:"sig"`
|
||||||
|
URL string `json:"url"`
|
||||||
|
}
|
||||||
|
|
||||||
|
type module struct {
|
||||||
|
Name string `json:"name"`
|
||||||
|
Items []*symbol `json:"items"`
|
||||||
|
}
|
||||||
|
|
||||||
|
func pydump(pyLib string) (mod module) {
|
||||||
|
var out bytes.Buffer
|
||||||
|
cmd := exec.Command("pydump", pyLib)
|
||||||
|
cmd.Stdout = &out
|
||||||
|
cmd.Stderr = os.Stderr
|
||||||
|
cmd.Run()
|
||||||
|
|
||||||
|
json.Unmarshal(out.Bytes(), &mod)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
func pysigfetch(pyLib string, names []string) (mod module) {
|
||||||
|
var out bytes.Buffer
|
||||||
|
cmd := exec.Command("pysigfetch", pyLib, "-")
|
||||||
|
cmd.Stdin = strings.NewReader(strings.Join(names, " "))
|
||||||
|
cmd.Stdout = &out
|
||||||
|
cmd.Stderr = os.Stderr
|
||||||
|
cmd.Run()
|
||||||
|
|
||||||
|
json.Unmarshal(out.Bytes(), &mod)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
if len(os.Args) < 2 {
|
||||||
|
fmt.Fprintln(os.Stderr, "Usage: llpyg <pythonLibPath>")
|
||||||
|
return
|
||||||
|
}
|
||||||
|
pyLib := os.Args[1]
|
||||||
|
|
||||||
|
mod := pydump(pyLib)
|
||||||
|
if mod.Name != pyLib {
|
||||||
|
log.Printf("import module %s failed\n", pyLib)
|
||||||
|
os.Exit(1)
|
||||||
|
}
|
||||||
|
pkg := gogen.NewPackage("", pkgName(pyLib), nil)
|
||||||
|
pkg.Import("unsafe").MarkForceUsed(pkg) // import _ "unsafe"
|
||||||
|
py := pkg.Import("github.com/goplus/llgo/py") // import "github.com/goplus/llgo/py"
|
||||||
|
|
||||||
|
f := func(cb *gogen.CodeBuilder) int {
|
||||||
|
cb.Val("py." + mod.Name)
|
||||||
|
return 1
|
||||||
|
}
|
||||||
|
defs := pkg.NewConstDefs(pkg.Types.Scope())
|
||||||
|
defs.New(f, 0, 0, nil, "LLGoPackage")
|
||||||
|
|
||||||
|
obj := py.Ref("Object").(*types.TypeName).Type().(*types.Named)
|
||||||
|
objPtr := types.NewPointer(obj)
|
||||||
|
ret := types.NewTuple(pkg.NewParam(0, "", objPtr))
|
||||||
|
|
||||||
|
ctx := &context{pkg, obj, objPtr, ret, nil, py}
|
||||||
|
ctx.genMod(pkg, &mod)
|
||||||
|
skips := ctx.skips
|
||||||
|
if n := len(skips); n > 0 {
|
||||||
|
log.Printf("==> There are %d signatures not found, fetch from doc site\n", n)
|
||||||
|
mod = pysigfetch(pyLib, skips)
|
||||||
|
ctx.skips = skips[:0]
|
||||||
|
ctx.genMod(pkg, &mod)
|
||||||
|
if len(mod.Items) > 0 {
|
||||||
|
skips = ctx.skips
|
||||||
|
}
|
||||||
|
if n := len(skips); n > 0 {
|
||||||
|
log.Printf("==> Skip %d symbols:\n%v\n", n, skips)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pkg.WriteTo(os.Stdout)
|
||||||
|
}
|
||||||
|
|
||||||
|
func pkgName(pyLib string) string {
|
||||||
|
if pos := strings.LastIndexByte(pyLib, '.'); pos >= 0 {
|
||||||
|
return pyLib[pos+1:]
|
||||||
|
}
|
||||||
|
return pyLib
|
||||||
|
}
|
||||||
|
|
||||||
|
type context struct {
|
||||||
|
pkg *gogen.Package
|
||||||
|
obj *types.Named
|
||||||
|
objPtr *types.Pointer
|
||||||
|
ret *types.Tuple
|
||||||
|
skips []string
|
||||||
|
py gogen.PkgRef
|
||||||
|
}
|
||||||
|
|
||||||
|
func (ctx *context) genMod(pkg *gogen.Package, mod *module) {
|
||||||
|
for _, sym := range mod.Items {
|
||||||
|
switch sym.Type {
|
||||||
|
case "builtin_function_or_method", "function", "method", "ufunc", "method-wrapper":
|
||||||
|
ctx.genFunc(pkg, sym)
|
||||||
|
case "str", "float", "bool", "type", "dict", "tuple", "list", "object", "module",
|
||||||
|
"int", "set", "frozenset", "flags", "bool_", "pybind11_type", "layout",
|
||||||
|
"memory_format", "qscheme", "dtype", "tensortype", "ellipsis": // skip
|
||||||
|
case "": // pysigfetch: page not found
|
||||||
|
ctx.skips = append(ctx.skips, sym.Name)
|
||||||
|
default:
|
||||||
|
t := sym.Type
|
||||||
|
if len(t) > 0 && (t[0] >= 'a' && t[0] <= 'z') && !strings.HasSuffix(t, "_info") {
|
||||||
|
log.Panicln("unsupport type:", sym.Type)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func (ctx *context) genFunc(pkg *gogen.Package, sym *symbol) {
|
||||||
|
name, symSig := sym.Name, sym.Sig
|
||||||
|
if len(name) == 0 || name[0] == '_' {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
if symSig == "<NULL>" {
|
||||||
|
ctx.skips = append(ctx.skips, name)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
params, variadic := ctx.genParams(pkg, symSig)
|
||||||
|
name = genName(name, -1)
|
||||||
|
sig := types.NewSignatureType(nil, nil, nil, params, ctx.ret, variadic)
|
||||||
|
fn := pkg.NewFuncDecl(token.NoPos, name, sig)
|
||||||
|
list := ctx.genDoc(sym.Doc)
|
||||||
|
if sym.URL != "" {
|
||||||
|
if len(list) > 0 {
|
||||||
|
list = append(list, emptyCommentLine)
|
||||||
|
}
|
||||||
|
list = append(list, genSee(sym.URL))
|
||||||
|
}
|
||||||
|
if len(list) > 0 {
|
||||||
|
list = append(list, emptyCommentLine)
|
||||||
|
}
|
||||||
|
list = append(list, ctx.genLinkname(name, sym))
|
||||||
|
fn.SetComments(pkg, &ast.CommentGroup{List: list})
|
||||||
|
// fn.BodyStart(pkg).End()
|
||||||
|
}
|
||||||
|
|
||||||
|
func (ctx *context) genParams(pkg *gogen.Package, sig string) (*types.Tuple, bool) {
|
||||||
|
args := pysig.Parse(sig)
|
||||||
|
if len(args) == 0 {
|
||||||
|
return nil, false
|
||||||
|
}
|
||||||
|
n := len(args)
|
||||||
|
objPtr := ctx.objPtr
|
||||||
|
list := make([]*types.Var, 0, n)
|
||||||
|
for i := 0; i < n; i++ {
|
||||||
|
name := args[i].Name
|
||||||
|
if name == "/" {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
if name == "*" || name == "\\*" {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
if strings.HasPrefix(name, "*") {
|
||||||
|
if name[1] != '*' {
|
||||||
|
list = append(list, ssa.VArg())
|
||||||
|
return types.NewTuple(list...), true
|
||||||
|
}
|
||||||
|
return types.NewTuple(list...), false
|
||||||
|
}
|
||||||
|
list = append(list, pkg.NewParam(0, genName(name, 0), objPtr))
|
||||||
|
}
|
||||||
|
return types.NewTuple(list...), false
|
||||||
|
}
|
||||||
|
|
||||||
|
func genName(name string, idxDontTitle int) string {
|
||||||
|
parts := strings.Split(name, "_")
|
||||||
|
for i, part := range parts {
|
||||||
|
if i != idxDontTitle && part != "" {
|
||||||
|
if c := part[0]; c >= 'a' && c <= 'z' {
|
||||||
|
part = string(c+'A'-'a') + part[1:]
|
||||||
|
}
|
||||||
|
parts[i] = part
|
||||||
|
}
|
||||||
|
}
|
||||||
|
name = strings.Join(parts, "")
|
||||||
|
switch name {
|
||||||
|
case "default", "func", "var", "range", "":
|
||||||
|
name += "_"
|
||||||
|
}
|
||||||
|
return name
|
||||||
|
}
|
||||||
|
|
||||||
|
func (ctx *context) genLinkname(name string, sym *symbol) *ast.Comment {
|
||||||
|
return &ast.Comment{Text: "//go:linkname " + name + " py." + sym.Name}
|
||||||
|
}
|
||||||
|
|
||||||
|
func (ctx *context) genDoc(doc string) []*ast.Comment {
|
||||||
|
if doc == "" {
|
||||||
|
return make([]*ast.Comment, 0, 4)
|
||||||
|
}
|
||||||
|
lines := strings.Split(doc, "\n")
|
||||||
|
list := make([]*ast.Comment, len(lines), len(lines)+4)
|
||||||
|
for i, line := range lines {
|
||||||
|
list[i] = &ast.Comment{Text: "// " + line}
|
||||||
|
}
|
||||||
|
return list
|
||||||
|
}
|
||||||
|
|
||||||
|
func genSee(url string) *ast.Comment {
|
||||||
|
return &ast.Comment{Text: "// See " + url}
|
||||||
|
}
|
||||||
|
|
||||||
|
var (
|
||||||
|
emptyCommentLine = &ast.Comment{Text: "//"}
|
||||||
|
)
|
||||||
100
chore/llpyg/pysig/parse.go
Normal file
100
chore/llpyg/pysig/parse.go
Normal file
@@ -0,0 +1,100 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2024 The GoPlus Authors (goplus.org). All rights reserved.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package pysig
|
||||||
|
|
||||||
|
import (
|
||||||
|
"strings"
|
||||||
|
)
|
||||||
|
|
||||||
|
type Arg struct {
|
||||||
|
Name string
|
||||||
|
Type string
|
||||||
|
DefVal string
|
||||||
|
}
|
||||||
|
|
||||||
|
// Parse parses a Python function signature.
|
||||||
|
func Parse(sig string) (args []*Arg) {
|
||||||
|
sig = strings.TrimPrefix(sig, "(")
|
||||||
|
for {
|
||||||
|
pos := strings.IndexAny(sig, ",:=)")
|
||||||
|
if pos <= 0 {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
arg := &Arg{Name: strings.TrimSpace(sig[:pos])}
|
||||||
|
args = append(args, arg)
|
||||||
|
c := sig[pos]
|
||||||
|
sig = sig[pos+1:]
|
||||||
|
switch c {
|
||||||
|
case ',':
|
||||||
|
continue
|
||||||
|
case ':':
|
||||||
|
arg.Type, sig = parseType(sig)
|
||||||
|
if strings.HasPrefix(sig, "=") {
|
||||||
|
arg.DefVal, sig = parseDefVal(sig[1:])
|
||||||
|
}
|
||||||
|
case '=':
|
||||||
|
arg.DefVal, sig = parseDefVal(sig)
|
||||||
|
case ')':
|
||||||
|
return
|
||||||
|
}
|
||||||
|
sig = strings.TrimPrefix(sig, ",")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const (
|
||||||
|
allSpecials = "([<'\""
|
||||||
|
)
|
||||||
|
|
||||||
|
var pairStops = map[byte]string{
|
||||||
|
'(': ")" + allSpecials,
|
||||||
|
'[': "]" + allSpecials,
|
||||||
|
'<': ">" + allSpecials,
|
||||||
|
'\'': "'" + allSpecials,
|
||||||
|
'"': "\"",
|
||||||
|
}
|
||||||
|
|
||||||
|
func parseText(sig string, stops string) (left string) {
|
||||||
|
for {
|
||||||
|
pos := strings.IndexAny(sig, stops)
|
||||||
|
if pos < 0 {
|
||||||
|
return sig
|
||||||
|
}
|
||||||
|
if c := sig[pos]; c != stops[0] {
|
||||||
|
if pstop, ok := pairStops[c]; ok {
|
||||||
|
sig = strings.TrimPrefix(parseText(sig[pos+1:], pstop), pstop[:1])
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return sig[pos:]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// stops: "=,)"
|
||||||
|
func parseType(sig string) (string, string) {
|
||||||
|
left := parseText(sig, "=,)"+allSpecials)
|
||||||
|
return resultOf(sig, left), left
|
||||||
|
}
|
||||||
|
|
||||||
|
// stops: ",)"
|
||||||
|
func parseDefVal(sig string) (string, string) {
|
||||||
|
left := parseText(sig, ",)"+allSpecials)
|
||||||
|
return resultOf(sig, left), left
|
||||||
|
}
|
||||||
|
|
||||||
|
func resultOf(sig, left string) string {
|
||||||
|
return strings.TrimSpace(sig[:len(sig)-len(left)])
|
||||||
|
}
|
||||||
52
chore/llpyg/pysig/parse_test.go
Normal file
52
chore/llpyg/pysig/parse_test.go
Normal file
@@ -0,0 +1,52 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2024 The GoPlus Authors (goplus.org). All rights reserved.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package pysig
|
||||||
|
|
||||||
|
import "testing"
|
||||||
|
|
||||||
|
func TestParse(t *testing.T) {
|
||||||
|
type testCase struct {
|
||||||
|
sig string
|
||||||
|
args []*Arg
|
||||||
|
}
|
||||||
|
cases := []testCase{
|
||||||
|
{"(start=None, *, unit: 'str | None' = None) -> 'TimedeltaIndex'", []*Arg{
|
||||||
|
{Name: "start", DefVal: "None"},
|
||||||
|
{Name: "*"},
|
||||||
|
{Name: "unit", Type: "'str | None'", DefVal: "None"},
|
||||||
|
}},
|
||||||
|
{"()", nil},
|
||||||
|
{"(a =", []*Arg{{Name: "a"}}},
|
||||||
|
{"(a) -> int", []*Arg{{Name: "a"}}},
|
||||||
|
{"(a: int)", []*Arg{{Name: "a", Type: "int"}}},
|
||||||
|
{"(a: int = 1, b: float)", []*Arg{{Name: "a", Type: "int", DefVal: "1"}, {Name: "b", Type: "float"}}},
|
||||||
|
{"(a = <1>, b = 2.0)", []*Arg{{Name: "a", DefVal: "<1>"}, {Name: "b", DefVal: "2.0"}}},
|
||||||
|
{"(a: 'Suffixes' = ('_x', '_y'))", []*Arg{{Name: "a", Type: "'Suffixes'", DefVal: "('_x', '_y')"}}},
|
||||||
|
}
|
||||||
|
for _, c := range cases {
|
||||||
|
args := Parse(c.sig)
|
||||||
|
if len(args) != len(c.args) {
|
||||||
|
t.Fatalf("%s: len(args) = %v, want %v", c.sig, len(args), len(c.args))
|
||||||
|
}
|
||||||
|
for i, arg := range args {
|
||||||
|
want := c.args[i]
|
||||||
|
if arg.Name != want.Name || arg.Type != want.Type || arg.DefVal != want.DefVal {
|
||||||
|
t.Fatalf("%s: args[%v] = %v, want %v", c.sig, i, arg, want)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
18
chore/llvmtargets/llvm_targets.go
Normal file
18
chore/llvmtargets/llvm_targets.go
Normal file
@@ -0,0 +1,18 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
|
||||||
|
"github.com/goplus/llvm"
|
||||||
|
)
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
llvm.InitializeAllTargetInfos()
|
||||||
|
llvm.InitializeAllTargets()
|
||||||
|
llvm.InitializeAllTargetMCs()
|
||||||
|
llvm.InitializeNativeTarget()
|
||||||
|
fmt.Println("targets:")
|
||||||
|
for it := llvm.FirstTarget(); it.C != nil; it = it.NextTarget() {
|
||||||
|
fmt.Printf("- %s: %s\n", it.Name(), it.Description())
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -18,14 +18,14 @@ _llgo_2: ; preds = %_llgo_1, %_llgo_0
|
|||||||
ret void
|
ret void
|
||||||
}
|
}
|
||||||
|
|
||||||
define void @main(i32 %0, ptr %1) {
|
define i32 @main(i32 %0, ptr %1) {
|
||||||
_llgo_0:
|
_llgo_0:
|
||||||
store i32 %0, ptr @__llgo_argc, align 4
|
store i32 %0, ptr @__llgo_argc, align 4
|
||||||
store ptr %1, ptr @__llgo_argv, align 8
|
store ptr %1, ptr @__llgo_argv, align 8
|
||||||
call void @"github.com/goplus/llgo/internal/runtime.init"()
|
call void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
call void @main.init()
|
call void @main.init()
|
||||||
%2 = call i64 @main.max(i64 1, i64 2)
|
%2 = call i64 @main.max(i64 1, i64 2)
|
||||||
ret void
|
ret i32 0
|
||||||
}
|
}
|
||||||
|
|
||||||
define i64 @main.max(i64 %0, i64 %1) {
|
define i64 @main.max(i64 %0, i64 %1) {
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
; ModuleID = 'main'
|
; ModuleID = 'main'
|
||||||
source_filename = "main"
|
source_filename = "main"
|
||||||
|
|
||||||
@main.hello = global ptr null
|
@main.hello = global [7 x i8] undef
|
||||||
@"main.init$guard" = global ptr null
|
@"main.init$guard" = global ptr null
|
||||||
@__llgo_argc = global ptr null
|
@__llgo_argc = global ptr null
|
||||||
@__llgo_argv = global ptr null
|
@__llgo_argv = global ptr null
|
||||||
@@ -27,7 +27,7 @@ _llgo_2: ; preds = %_llgo_1, %_llgo_0
|
|||||||
ret void
|
ret void
|
||||||
}
|
}
|
||||||
|
|
||||||
define void @main(i32 %0, ptr %1) {
|
define i32 @main(i32 %0, ptr %1) {
|
||||||
_llgo_0:
|
_llgo_0:
|
||||||
store i32 %0, ptr @__llgo_argc, align 4
|
store i32 %0, ptr @__llgo_argc, align 4
|
||||||
store ptr %1, ptr @__llgo_argv, align 8
|
store ptr %1, ptr @__llgo_argv, align 8
|
||||||
@@ -35,7 +35,7 @@ _llgo_0:
|
|||||||
call void @main.init()
|
call void @main.init()
|
||||||
%2 = call i64 @"github.com/goplus/llgo/cl/internal/stdio.Max"(i64 2, i64 100)
|
%2 = call i64 @"github.com/goplus/llgo/cl/internal/stdio.Max"(i64 2, i64 100)
|
||||||
call void (ptr, ...) @printf(ptr @main.hello)
|
call void (ptr, ...) @printf(ptr @main.hello)
|
||||||
ret void
|
ret i32 0
|
||||||
}
|
}
|
||||||
|
|
||||||
declare void @"github.com/goplus/llgo/cl/internal/stdio.init"()
|
declare void @"github.com/goplus/llgo/cl/internal/stdio.init"()
|
||||||
|
|||||||
@@ -1,21 +1,21 @@
|
|||||||
; ModuleID = 'main'
|
; ModuleID = 'main'
|
||||||
source_filename = "main"
|
source_filename = "main"
|
||||||
|
|
||||||
@main.format = global ptr null
|
@main.format = global [10 x i8] undef
|
||||||
@"main.init$guard" = global ptr null
|
@"main.init$guard" = global ptr null
|
||||||
@__llgo_argc = global ptr null
|
@__llgo_argc = global ptr null
|
||||||
@__llgo_argv = global ptr null
|
@__llgo_argv = global ptr null
|
||||||
|
|
||||||
define i64 @"(main.T).Add"(i64 %0, i64 %1) {
|
define i64 @main.T.Add(i64 %0, i64 %1) {
|
||||||
_llgo_0:
|
_llgo_0:
|
||||||
%2 = add i64 %0, %1
|
%2 = add i64 %0, %1
|
||||||
ret i64 %2
|
ret i64 %2
|
||||||
}
|
}
|
||||||
|
|
||||||
define i64 @"(*main.T).Add"(ptr %0, i64 %1) {
|
define i64 @"main.(*T).Add"(ptr %0, i64 %1) {
|
||||||
_llgo_0:
|
_llgo_0:
|
||||||
%2 = load i64, ptr %0, align 4
|
%2 = load i64, ptr %0, align 4
|
||||||
%3 = call i64 @"(main.T).Add"(i64 %2, i64 %1)
|
%3 = call i64 @main.T.Add(i64 %2, i64 %1)
|
||||||
ret i64 %3
|
ret i64 %3
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -42,15 +42,15 @@ _llgo_2: ; preds = %_llgo_1, %_llgo_0
|
|||||||
ret void
|
ret void
|
||||||
}
|
}
|
||||||
|
|
||||||
define void @main(i32 %0, ptr %1) {
|
define i32 @main(i32 %0, ptr %1) {
|
||||||
_llgo_0:
|
_llgo_0:
|
||||||
store i32 %0, ptr @__llgo_argc, align 4
|
store i32 %0, ptr @__llgo_argc, align 4
|
||||||
store ptr %1, ptr @__llgo_argv, align 8
|
store ptr %1, ptr @__llgo_argv, align 8
|
||||||
call void @"github.com/goplus/llgo/internal/runtime.init"()
|
call void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
call void @main.init()
|
call void @main.init()
|
||||||
%2 = call i64 @"(main.T).Add"(i64 1, i64 2)
|
%2 = call i64 @main.T.Add(i64 1, i64 2)
|
||||||
call void (ptr, ...) @printf(ptr @main.format, i64 %2)
|
call void (ptr, ...) @printf(ptr @main.format, i64 %2)
|
||||||
ret void
|
ret i32 0
|
||||||
}
|
}
|
||||||
|
|
||||||
declare void @"github.com/goplus/llgo/internal/runtime.init"()
|
declare void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
@@ -1,7 +1,7 @@
|
|||||||
; ModuleID = 'main'
|
; ModuleID = 'main'
|
||||||
source_filename = "main"
|
source_filename = "main"
|
||||||
|
|
||||||
@main.hello = global ptr null
|
@main.hello = global [7 x i8] undef
|
||||||
@"main.init$guard" = global ptr null
|
@"main.init$guard" = global ptr null
|
||||||
@__llgo_argc = global ptr null
|
@__llgo_argc = global ptr null
|
||||||
@__llgo_argv = global ptr null
|
@__llgo_argv = global ptr null
|
||||||
@@ -26,14 +26,14 @@ _llgo_2: ; preds = %_llgo_1, %_llgo_0
|
|||||||
ret void
|
ret void
|
||||||
}
|
}
|
||||||
|
|
||||||
define void @main(i32 %0, ptr %1) {
|
define i32 @main(i32 %0, ptr %1) {
|
||||||
_llgo_0:
|
_llgo_0:
|
||||||
store i32 %0, ptr @__llgo_argc, align 4
|
store i32 %0, ptr @__llgo_argc, align 4
|
||||||
store ptr %1, ptr @__llgo_argv, align 8
|
store ptr %1, ptr @__llgo_argv, align 8
|
||||||
call void @"github.com/goplus/llgo/internal/runtime.init"()
|
call void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
call void @main.init()
|
call void @main.init()
|
||||||
call void (ptr, ...) @printf(ptr @main.hello)
|
call void (ptr, ...) @printf(ptr @main.hello)
|
||||||
ret void
|
ret i32 0
|
||||||
}
|
}
|
||||||
|
|
||||||
declare void @"github.com/goplus/llgo/internal/runtime.init"()
|
declare void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
; ModuleID = 'main'
|
; ModuleID = 'main'
|
||||||
source_filename = "main"
|
source_filename = "main"
|
||||||
|
|
||||||
@main.format = global ptr null
|
@main.format = global [10 x i8] undef
|
||||||
@"main.init$guard" = global ptr null
|
@"main.init$guard" = global ptr null
|
||||||
@__llgo_argc = global ptr null
|
@__llgo_argc = global ptr null
|
||||||
@__llgo_argv = global ptr null
|
@__llgo_argv = global ptr null
|
||||||
@@ -29,14 +29,14 @@ _llgo_2: ; preds = %_llgo_1, %_llgo_0
|
|||||||
ret void
|
ret void
|
||||||
}
|
}
|
||||||
|
|
||||||
define void @main(i32 %0, ptr %1) {
|
define i32 @main(i32 %0, ptr %1) {
|
||||||
_llgo_0:
|
_llgo_0:
|
||||||
store i32 %0, ptr @__llgo_argc, align 4
|
store i32 %0, ptr @__llgo_argc, align 4
|
||||||
store ptr %1, ptr @__llgo_argv, align 8
|
store ptr %1, ptr @__llgo_argv, align 8
|
||||||
call void @"github.com/goplus/llgo/internal/runtime.init"()
|
call void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
call void @main.init()
|
call void @main.init()
|
||||||
call void (ptr, ...) @printf(ptr @main.format, i64 100)
|
call void (ptr, ...) @printf(ptr @main.format, i64 100)
|
||||||
ret void
|
ret i32 0
|
||||||
}
|
}
|
||||||
|
|
||||||
declare void @"github.com/goplus/llgo/internal/runtime.init"()
|
declare void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
|
|||||||
@@ -1,12 +1,12 @@
|
|||||||
; ModuleID = 'main'
|
; ModuleID = 'main'
|
||||||
source_filename = "main"
|
source_filename = "main"
|
||||||
|
|
||||||
@main.format = global ptr null
|
@main.format = global [10 x i8] undef
|
||||||
@"main.init$guard" = global ptr null
|
@"main.init$guard" = global ptr null
|
||||||
@__llgo_argc = global ptr null
|
@__llgo_argc = global ptr null
|
||||||
@__llgo_argv = global ptr null
|
@__llgo_argv = global ptr null
|
||||||
|
|
||||||
define void @"(*main.T).Print"(ptr %0, i64 %1) {
|
define void @"main.(*T).Print"(ptr %0, i64 %1) {
|
||||||
_llgo_0:
|
_llgo_0:
|
||||||
call void (ptr, ...) @printf(ptr %0, i64 %1)
|
call void (ptr, ...) @printf(ptr %0, i64 %1)
|
||||||
ret void
|
ret void
|
||||||
@@ -35,14 +35,14 @@ _llgo_2: ; preds = %_llgo_1, %_llgo_0
|
|||||||
ret void
|
ret void
|
||||||
}
|
}
|
||||||
|
|
||||||
define void @main(i32 %0, ptr %1) {
|
define i32 @main(i32 %0, ptr %1) {
|
||||||
_llgo_0:
|
_llgo_0:
|
||||||
store i32 %0, ptr @__llgo_argc, align 4
|
store i32 %0, ptr @__llgo_argc, align 4
|
||||||
store ptr %1, ptr @__llgo_argv, align 8
|
store ptr %1, ptr @__llgo_argv, align 8
|
||||||
call void @"github.com/goplus/llgo/internal/runtime.init"()
|
call void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
call void @main.init()
|
call void @main.init()
|
||||||
call void @"(*main.T).Print"(ptr @main.format, i64 100)
|
call void @"main.(*T).Print"(ptr @main.format, i64 100)
|
||||||
ret void
|
ret i32 0
|
||||||
}
|
}
|
||||||
|
|
||||||
declare void @printf(ptr, ...)
|
declare void @printf(ptr, ...)
|
||||||
|
|||||||
@@ -25,7 +25,7 @@ _llgo_2: ; preds = %_llgo_1, %_llgo_0
|
|||||||
ret void
|
ret void
|
||||||
}
|
}
|
||||||
|
|
||||||
define void @main(i32 %0, ptr %1) {
|
define i32 @main(i32 %0, ptr %1) {
|
||||||
_llgo_0:
|
_llgo_0:
|
||||||
store i32 %0, ptr @__llgo_argc, align 4
|
store i32 %0, ptr @__llgo_argc, align 4
|
||||||
store ptr %1, ptr @__llgo_argv, align 8
|
store ptr %1, ptr @__llgo_argv, align 8
|
||||||
@@ -33,7 +33,7 @@ _llgo_0:
|
|||||||
call void @main.init()
|
call void @main.init()
|
||||||
%2 = call i32 @main.f(i32 100)
|
%2 = call i32 @main.f(i32 100)
|
||||||
%3 = call i32 (ptr, ...) @printf(ptr @0, i32 %2)
|
%3 = call i32 (ptr, ...) @printf(ptr @0, i32 %2)
|
||||||
ret void
|
ret i32 0
|
||||||
}
|
}
|
||||||
|
|
||||||
declare void @"github.com/goplus/llgo/internal/runtime.init"()
|
declare void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
|
|||||||
@@ -20,7 +20,7 @@ _llgo_2: ; preds = %_llgo_1, %_llgo_0
|
|||||||
ret void
|
ret void
|
||||||
}
|
}
|
||||||
|
|
||||||
define void @main(i32 %0, ptr %1) {
|
define i32 @main(i32 %0, ptr %1) {
|
||||||
_llgo_0:
|
_llgo_0:
|
||||||
store i32 %0, ptr @__llgo_argc, align 4
|
store i32 %0, ptr @__llgo_argc, align 4
|
||||||
store ptr %1, ptr @__llgo_argv, align 8
|
store ptr %1, ptr @__llgo_argv, align 8
|
||||||
@@ -33,7 +33,7 @@ _llgo_1: ; preds = %_llgo_0
|
|||||||
br label %_llgo_2
|
br label %_llgo_2
|
||||||
|
|
||||||
_llgo_2: ; preds = %_llgo_1, %_llgo_0
|
_llgo_2: ; preds = %_llgo_1, %_llgo_0
|
||||||
ret void
|
ret i32 0
|
||||||
}
|
}
|
||||||
|
|
||||||
declare void @"github.com/goplus/llgo/internal/runtime.init"()
|
declare void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
|
|||||||
23
cl/_testdata/utf8/in.go
Normal file
23
cl/_testdata/utf8/in.go
Normal file
@@ -0,0 +1,23 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"unicode/utf8"
|
||||||
|
)
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
var str = "中abcd"
|
||||||
|
for i := 0; i < len(str); {
|
||||||
|
r, n := utf8.DecodeRuneInString(str[i:])
|
||||||
|
i += n
|
||||||
|
println(r)
|
||||||
|
}
|
||||||
|
println(index(2) == 3)
|
||||||
|
}
|
||||||
|
|
||||||
|
var array = [...]uint8{
|
||||||
|
1, 2, 3, 4, 5, 6, 7, 8,
|
||||||
|
}
|
||||||
|
|
||||||
|
func index(n int8) uint8 {
|
||||||
|
return array[n]
|
||||||
|
}
|
||||||
105
cl/_testdata/utf8/out.ll
Normal file
105
cl/_testdata/utf8/out.ll
Normal file
@@ -0,0 +1,105 @@
|
|||||||
|
; ModuleID = 'main'
|
||||||
|
source_filename = "main"
|
||||||
|
|
||||||
|
%"github.com/goplus/llgo/internal/runtime.String" = type { ptr, i64 }
|
||||||
|
|
||||||
|
@main.array = global [8 x i8] undef
|
||||||
|
@"main.init$guard" = global ptr null
|
||||||
|
@__llgo_argc = global ptr null
|
||||||
|
@__llgo_argv = global ptr null
|
||||||
|
@0 = private unnamed_addr constant [8 x i8] c"\E4\B8\ADabcd\00", align 1
|
||||||
|
@1 = private unnamed_addr constant [8 x i8] c"\E4\B8\ADabcd\00", align 1
|
||||||
|
|
||||||
|
define i8 @main.index(i8 %0) {
|
||||||
|
_llgo_0:
|
||||||
|
%1 = icmp slt i8 %0, 0
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.AssertIndexRange"(i1 %1)
|
||||||
|
%2 = zext i8 %0 to i64
|
||||||
|
%3 = getelementptr inbounds i8, ptr @main.array, i64 %2
|
||||||
|
%4 = load i8, ptr %3, align 1
|
||||||
|
ret i8 %4
|
||||||
|
}
|
||||||
|
|
||||||
|
define void @main.init() {
|
||||||
|
_llgo_0:
|
||||||
|
%0 = load i1, ptr @"main.init$guard", align 1
|
||||||
|
br i1 %0, label %_llgo_2, label %_llgo_1
|
||||||
|
|
||||||
|
_llgo_1: ; preds = %_llgo_0
|
||||||
|
store i1 true, ptr @"main.init$guard", align 1
|
||||||
|
call void @"unicode/utf8.init"()
|
||||||
|
store i8 1, ptr @main.array, align 1
|
||||||
|
store i8 2, ptr getelementptr inbounds (i8, ptr @main.array, i64 1), align 1
|
||||||
|
store i8 3, ptr getelementptr inbounds (i8, ptr @main.array, i64 2), align 1
|
||||||
|
store i8 4, ptr getelementptr inbounds (i8, ptr @main.array, i64 3), align 1
|
||||||
|
store i8 5, ptr getelementptr inbounds (i8, ptr @main.array, i64 4), align 1
|
||||||
|
store i8 6, ptr getelementptr inbounds (i8, ptr @main.array, i64 5), align 1
|
||||||
|
store i8 7, ptr getelementptr inbounds (i8, ptr @main.array, i64 6), align 1
|
||||||
|
store i8 8, ptr getelementptr inbounds (i8, ptr @main.array, i64 7), align 1
|
||||||
|
br label %_llgo_2
|
||||||
|
|
||||||
|
_llgo_2: ; preds = %_llgo_1, %_llgo_0
|
||||||
|
ret void
|
||||||
|
}
|
||||||
|
|
||||||
|
define i32 @main(i32 %0, ptr %1) {
|
||||||
|
_llgo_0:
|
||||||
|
store i32 %0, ptr @__llgo_argc, align 4
|
||||||
|
store ptr %1, ptr @__llgo_argv, align 8
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
|
call void @main.init()
|
||||||
|
br label %_llgo_3
|
||||||
|
|
||||||
|
_llgo_1: ; preds = %_llgo_3
|
||||||
|
%2 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%3 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %2, i32 0, i32 0
|
||||||
|
store ptr @1, ptr %3, align 8
|
||||||
|
%4 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %2, i32 0, i32 1
|
||||||
|
store i64 7, ptr %4, align 4
|
||||||
|
%5 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %2, align 8
|
||||||
|
%6 = extractvalue %"github.com/goplus/llgo/internal/runtime.String" %5, 1
|
||||||
|
%7 = call %"github.com/goplus/llgo/internal/runtime.String" @"github.com/goplus/llgo/internal/runtime.NewStringSlice"(%"github.com/goplus/llgo/internal/runtime.String" %5, i64 %15, i64 %6)
|
||||||
|
%8 = call { i32, i64 } @"unicode/utf8.DecodeRuneInString"(%"github.com/goplus/llgo/internal/runtime.String" %7)
|
||||||
|
%9 = extractvalue { i32, i64 } %8, 0
|
||||||
|
%10 = extractvalue { i32, i64 } %8, 1
|
||||||
|
%11 = add i64 %15, %10
|
||||||
|
%12 = sext i32 %9 to i64
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintInt"(i64 %12)
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintByte"(i8 10)
|
||||||
|
br label %_llgo_3
|
||||||
|
|
||||||
|
_llgo_2: ; preds = %_llgo_3
|
||||||
|
%13 = call i8 @main.index(i8 2)
|
||||||
|
%14 = icmp eq i8 %13, 3
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintBool"(i1 %14)
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintByte"(i8 10)
|
||||||
|
ret i32 0
|
||||||
|
|
||||||
|
_llgo_3: ; preds = %_llgo_1, %_llgo_0
|
||||||
|
%15 = phi i64 [ 0, %_llgo_0 ], [ %11, %_llgo_1 ]
|
||||||
|
%16 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%17 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %16, i32 0, i32 0
|
||||||
|
store ptr @0, ptr %17, align 8
|
||||||
|
%18 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %16, i32 0, i32 1
|
||||||
|
store i64 7, ptr %18, align 4
|
||||||
|
%19 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %16, align 8
|
||||||
|
%20 = extractvalue %"github.com/goplus/llgo/internal/runtime.String" %19, 1
|
||||||
|
%21 = icmp slt i64 %15, %20
|
||||||
|
br i1 %21, label %_llgo_1, label %_llgo_2
|
||||||
|
}
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.AssertIndexRange"(i1)
|
||||||
|
|
||||||
|
declare void @"unicode/utf8.init"()
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
|
|
||||||
|
declare %"github.com/goplus/llgo/internal/runtime.String" @"github.com/goplus/llgo/internal/runtime.NewStringSlice"(%"github.com/goplus/llgo/internal/runtime.String", i64, i64)
|
||||||
|
|
||||||
|
declare { i32, i64 } @"unicode/utf8.DecodeRuneInString"(%"github.com/goplus/llgo/internal/runtime.String")
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.PrintInt"(i64)
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.PrintByte"(i8)
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.PrintBool"(i1)
|
||||||
@@ -1,13 +1,18 @@
|
|||||||
; ModuleID = 'main'
|
; ModuleID = 'main'
|
||||||
source_filename = "main"
|
source_filename = "main"
|
||||||
|
|
||||||
%"github.com/goplus/llgo/internal/runtime.iface" = type { ptr, ptr }
|
%"github.com/goplus/llgo/internal/runtime.eface" = type { ptr, ptr }
|
||||||
|
%"github.com/goplus/llgo/internal/abi.Type" = type { i64, i64, i32, i8, i8, i8, i8, { ptr, ptr }, ptr, %"github.com/goplus/llgo/internal/runtime.String", ptr }
|
||||||
|
%"github.com/goplus/llgo/internal/runtime.String" = type { ptr, i64 }
|
||||||
%"github.com/goplus/llgo/internal/runtime.Slice" = type { ptr, i64, i64 }
|
%"github.com/goplus/llgo/internal/runtime.Slice" = type { ptr, i64, i64 }
|
||||||
|
|
||||||
@"main.init$guard" = global ptr null
|
@"main.init$guard" = global ptr null
|
||||||
@__llgo_argc = global ptr null
|
@__llgo_argc = global ptr null
|
||||||
@__llgo_argv = global ptr null
|
@__llgo_argv = global ptr null
|
||||||
|
@_llgo_int = linkonce global ptr null
|
||||||
@0 = private unnamed_addr constant [4 x i8] c"%d\0A\00", align 1
|
@0 = private unnamed_addr constant [4 x i8] c"%d\0A\00", align 1
|
||||||
|
@1 = private unnamed_addr constant [22 x i8] c"type assertion failed\00", align 1
|
||||||
|
@_llgo_string = linkonce global ptr null
|
||||||
|
|
||||||
define void @main.init() {
|
define void @main.init() {
|
||||||
_llgo_0:
|
_llgo_0:
|
||||||
@@ -16,74 +21,157 @@ _llgo_0:
|
|||||||
|
|
||||||
_llgo_1: ; preds = %_llgo_0
|
_llgo_1: ; preds = %_llgo_0
|
||||||
store i1 true, ptr @"main.init$guard", align 1
|
store i1 true, ptr @"main.init$guard", align 1
|
||||||
|
call void @"main.init$after"()
|
||||||
br label %_llgo_2
|
br label %_llgo_2
|
||||||
|
|
||||||
_llgo_2: ; preds = %_llgo_1, %_llgo_0
|
_llgo_2: ; preds = %_llgo_1, %_llgo_0
|
||||||
ret void
|
ret void
|
||||||
}
|
}
|
||||||
|
|
||||||
define void @main(i32 %0, ptr %1) {
|
define i32 @main(i32 %0, ptr %1) {
|
||||||
_llgo_0:
|
_llgo_0:
|
||||||
store i32 %0, ptr @__llgo_argc, align 4
|
store i32 %0, ptr @__llgo_argc, align 4
|
||||||
store ptr %1, ptr @__llgo_argv, align 8
|
store ptr %1, ptr @__llgo_argv, align 8
|
||||||
call void @"github.com/goplus/llgo/internal/runtime.init"()
|
call void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
call void @main.init()
|
call void @main.init()
|
||||||
%2 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocZ"(i64 48)
|
%2 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocZ"(i64 48)
|
||||||
%3 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.iface", ptr %2, i64 0
|
%3 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.eface", ptr %2, i64 0
|
||||||
%4 = call ptr @"github.com/goplus/llgo/internal/runtime.Basic"(i64 2)
|
%4 = load ptr, ptr @_llgo_int, align 8
|
||||||
%5 = call %"github.com/goplus/llgo/internal/runtime.iface" @"github.com/goplus/llgo/internal/runtime.MakeAnyInt"(ptr %4, i64 1)
|
%5 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Type", ptr %4, i32 0, i32 6
|
||||||
store %"github.com/goplus/llgo/internal/runtime.iface" %5, ptr %3, align 8
|
%6 = load i8, ptr %5, align 1
|
||||||
%6 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.iface", ptr %2, i64 1
|
%7 = or i8 %6, 32
|
||||||
%7 = call ptr @"github.com/goplus/llgo/internal/runtime.Basic"(i64 2)
|
store i8 %7, ptr %5, align 1
|
||||||
%8 = call %"github.com/goplus/llgo/internal/runtime.iface" @"github.com/goplus/llgo/internal/runtime.MakeAnyInt"(ptr %7, i64 2)
|
%8 = alloca %"github.com/goplus/llgo/internal/runtime.eface", align 8
|
||||||
store %"github.com/goplus/llgo/internal/runtime.iface" %8, ptr %6, align 8
|
%9 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.eface", ptr %8, i32 0, i32 0
|
||||||
%9 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.iface", ptr %2, i64 2
|
store ptr %4, ptr %9, align 8
|
||||||
%10 = call ptr @"github.com/goplus/llgo/internal/runtime.Basic"(i64 2)
|
%10 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.eface", ptr %8, i32 0, i32 1
|
||||||
%11 = call %"github.com/goplus/llgo/internal/runtime.iface" @"github.com/goplus/llgo/internal/runtime.MakeAnyInt"(ptr %10, i64 3)
|
store ptr inttoptr (i64 1 to ptr), ptr %10, align 8
|
||||||
store %"github.com/goplus/llgo/internal/runtime.iface" %11, ptr %9, align 8
|
%11 = load %"github.com/goplus/llgo/internal/runtime.eface", ptr %8, align 8
|
||||||
%12 = call %"github.com/goplus/llgo/internal/runtime.Slice" @"github.com/goplus/llgo/internal/runtime.NewSlice3"(ptr %2, i64 16, i64 3, i64 0, i64 3, i64 3)
|
store %"github.com/goplus/llgo/internal/runtime.eface" %11, ptr %3, align 8
|
||||||
call void @main.test(%"github.com/goplus/llgo/internal/runtime.Slice" %12)
|
%12 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.eface", ptr %2, i64 1
|
||||||
ret void
|
%13 = load ptr, ptr @_llgo_int, align 8
|
||||||
|
%14 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Type", ptr %13, i32 0, i32 6
|
||||||
|
%15 = load i8, ptr %14, align 1
|
||||||
|
%16 = or i8 %15, 32
|
||||||
|
store i8 %16, ptr %14, align 1
|
||||||
|
%17 = alloca %"github.com/goplus/llgo/internal/runtime.eface", align 8
|
||||||
|
%18 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.eface", ptr %17, i32 0, i32 0
|
||||||
|
store ptr %13, ptr %18, align 8
|
||||||
|
%19 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.eface", ptr %17, i32 0, i32 1
|
||||||
|
store ptr inttoptr (i64 2 to ptr), ptr %19, align 8
|
||||||
|
%20 = load %"github.com/goplus/llgo/internal/runtime.eface", ptr %17, align 8
|
||||||
|
store %"github.com/goplus/llgo/internal/runtime.eface" %20, ptr %12, align 8
|
||||||
|
%21 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.eface", ptr %2, i64 2
|
||||||
|
%22 = load ptr, ptr @_llgo_int, align 8
|
||||||
|
%23 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Type", ptr %22, i32 0, i32 6
|
||||||
|
%24 = load i8, ptr %23, align 1
|
||||||
|
%25 = or i8 %24, 32
|
||||||
|
store i8 %25, ptr %23, align 1
|
||||||
|
%26 = alloca %"github.com/goplus/llgo/internal/runtime.eface", align 8
|
||||||
|
%27 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.eface", ptr %26, i32 0, i32 0
|
||||||
|
store ptr %22, ptr %27, align 8
|
||||||
|
%28 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.eface", ptr %26, i32 0, i32 1
|
||||||
|
store ptr inttoptr (i64 3 to ptr), ptr %28, align 8
|
||||||
|
%29 = load %"github.com/goplus/llgo/internal/runtime.eface", ptr %26, align 8
|
||||||
|
store %"github.com/goplus/llgo/internal/runtime.eface" %29, ptr %21, align 8
|
||||||
|
%30 = alloca %"github.com/goplus/llgo/internal/runtime.Slice", align 8
|
||||||
|
%31 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %30, i32 0, i32 0
|
||||||
|
store ptr %2, ptr %31, align 8
|
||||||
|
%32 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %30, i32 0, i32 1
|
||||||
|
store i64 3, ptr %32, align 4
|
||||||
|
%33 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %30, i32 0, i32 2
|
||||||
|
store i64 3, ptr %33, align 4
|
||||||
|
%34 = load %"github.com/goplus/llgo/internal/runtime.Slice", ptr %30, align 8
|
||||||
|
call void @main.test(%"github.com/goplus/llgo/internal/runtime.Slice" %34)
|
||||||
|
ret i32 0
|
||||||
}
|
}
|
||||||
|
|
||||||
define void @main.test(%"github.com/goplus/llgo/internal/runtime.Slice" %0) {
|
define void @main.test(%"github.com/goplus/llgo/internal/runtime.Slice" %0) {
|
||||||
_llgo_0:
|
_llgo_0:
|
||||||
%1 = call i64 @"github.com/goplus/llgo/internal/runtime.SliceLen"(%"github.com/goplus/llgo/internal/runtime.Slice" %0)
|
%1 = extractvalue %"github.com/goplus/llgo/internal/runtime.Slice" %0, 1
|
||||||
br label %_llgo_1
|
br label %_llgo_1
|
||||||
|
|
||||||
_llgo_1: ; preds = %_llgo_2, %_llgo_0
|
_llgo_1: ; preds = %_llgo_4, %_llgo_0
|
||||||
%2 = phi i64 [ -1, %_llgo_0 ], [ %3, %_llgo_2 ]
|
%2 = phi i64 [ -1, %_llgo_0 ], [ %3, %_llgo_4 ]
|
||||||
%3 = add i64 %2, 1
|
%3 = add i64 %2, 1
|
||||||
%4 = icmp slt i64 %3, %1
|
%4 = icmp slt i64 %3, %1
|
||||||
br i1 %4, label %_llgo_2, label %_llgo_3
|
br i1 %4, label %_llgo_2, label %_llgo_3
|
||||||
|
|
||||||
_llgo_2: ; preds = %_llgo_1
|
_llgo_2: ; preds = %_llgo_1
|
||||||
%5 = call ptr @"github.com/goplus/llgo/internal/runtime.SliceData"(%"github.com/goplus/llgo/internal/runtime.Slice" %0)
|
%5 = icmp slt i64 %3, 0
|
||||||
%6 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.iface", ptr %5, i64 %3
|
call void @"github.com/goplus/llgo/internal/runtime.AssertIndexRange"(i1 %5)
|
||||||
%7 = load %"github.com/goplus/llgo/internal/runtime.iface", ptr %6, align 8
|
%6 = extractvalue %"github.com/goplus/llgo/internal/runtime.Slice" %0, 0
|
||||||
%8 = call ptr @"github.com/goplus/llgo/internal/runtime.Basic"(i64 2)
|
%7 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.eface", ptr %6, i64 %3
|
||||||
%9 = call i64 @"github.com/goplus/llgo/internal/runtime.I2Int"(%"github.com/goplus/llgo/internal/runtime.iface" %7, ptr %8)
|
%8 = load %"github.com/goplus/llgo/internal/runtime.eface", ptr %7, align 8
|
||||||
%10 = call i32 (ptr, ...) @printf(ptr @0, i64 %9)
|
%9 = extractvalue %"github.com/goplus/llgo/internal/runtime.eface" %8, 0
|
||||||
br label %_llgo_1
|
%10 = load ptr, ptr @_llgo_int, align 8
|
||||||
|
%11 = icmp eq ptr %9, %10
|
||||||
|
br i1 %11, label %_llgo_4, label %_llgo_5
|
||||||
|
|
||||||
_llgo_3: ; preds = %_llgo_1
|
_llgo_3: ; preds = %_llgo_1
|
||||||
ret void
|
ret void
|
||||||
|
|
||||||
|
_llgo_4: ; preds = %_llgo_2
|
||||||
|
%12 = extractvalue %"github.com/goplus/llgo/internal/runtime.eface" %8, 1
|
||||||
|
%13 = ptrtoint ptr %12 to i64
|
||||||
|
%14 = call i32 (ptr, ...) @printf(ptr @0, i64 %13)
|
||||||
|
br label %_llgo_1
|
||||||
|
|
||||||
|
_llgo_5: ; preds = %_llgo_2
|
||||||
|
%15 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%16 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %15, i32 0, i32 0
|
||||||
|
store ptr @1, ptr %16, align 8
|
||||||
|
%17 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %15, i32 0, i32 1
|
||||||
|
store i64 21, ptr %17, align 4
|
||||||
|
%18 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %15, align 8
|
||||||
|
%19 = load ptr, ptr @_llgo_string, align 8
|
||||||
|
%20 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocU"(i64 16)
|
||||||
|
store %"github.com/goplus/llgo/internal/runtime.String" %18, ptr %20, align 8
|
||||||
|
%21 = alloca %"github.com/goplus/llgo/internal/runtime.eface", align 8
|
||||||
|
%22 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.eface", ptr %21, i32 0, i32 0
|
||||||
|
store ptr %19, ptr %22, align 8
|
||||||
|
%23 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.eface", ptr %21, i32 0, i32 1
|
||||||
|
store ptr %20, ptr %23, align 8
|
||||||
|
%24 = load %"github.com/goplus/llgo/internal/runtime.eface", ptr %21, align 8
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.Panic"(%"github.com/goplus/llgo/internal/runtime.eface" %24)
|
||||||
|
unreachable
|
||||||
}
|
}
|
||||||
|
|
||||||
declare void @"github.com/goplus/llgo/internal/runtime.init"()
|
declare void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
|
|
||||||
declare ptr @"github.com/goplus/llgo/internal/runtime.AllocZ"(i64)
|
declare ptr @"github.com/goplus/llgo/internal/runtime.AllocZ"(i64)
|
||||||
|
|
||||||
|
define void @"main.init$after"() {
|
||||||
|
_llgo_0:
|
||||||
|
%0 = load ptr, ptr @_llgo_int, align 8
|
||||||
|
%1 = icmp eq ptr %0, null
|
||||||
|
br i1 %1, label %_llgo_1, label %_llgo_2
|
||||||
|
|
||||||
|
_llgo_1: ; preds = %_llgo_0
|
||||||
|
%2 = call ptr @"github.com/goplus/llgo/internal/runtime.Basic"(i64 2)
|
||||||
|
store ptr %2, ptr @_llgo_int, align 8
|
||||||
|
br label %_llgo_2
|
||||||
|
|
||||||
|
_llgo_2: ; preds = %_llgo_1, %_llgo_0
|
||||||
|
%3 = load ptr, ptr @_llgo_string, align 8
|
||||||
|
%4 = icmp eq ptr %3, null
|
||||||
|
br i1 %4, label %_llgo_3, label %_llgo_4
|
||||||
|
|
||||||
|
_llgo_3: ; preds = %_llgo_2
|
||||||
|
%5 = call ptr @"github.com/goplus/llgo/internal/runtime.Basic"(i64 24)
|
||||||
|
store ptr %5, ptr @_llgo_string, align 8
|
||||||
|
br label %_llgo_4
|
||||||
|
|
||||||
|
_llgo_4: ; preds = %_llgo_3, %_llgo_2
|
||||||
|
ret void
|
||||||
|
}
|
||||||
|
|
||||||
declare ptr @"github.com/goplus/llgo/internal/runtime.Basic"(i64)
|
declare ptr @"github.com/goplus/llgo/internal/runtime.Basic"(i64)
|
||||||
|
|
||||||
declare %"github.com/goplus/llgo/internal/runtime.iface" @"github.com/goplus/llgo/internal/runtime.MakeAnyInt"(ptr, i64)
|
declare void @"github.com/goplus/llgo/internal/runtime.AssertIndexRange"(i1)
|
||||||
|
|
||||||
declare %"github.com/goplus/llgo/internal/runtime.Slice" @"github.com/goplus/llgo/internal/runtime.NewSlice3"(ptr, i64, i64, i64, i64, i64)
|
declare ptr @"github.com/goplus/llgo/internal/runtime.AllocU"(i64)
|
||||||
|
|
||||||
declare i64 @"github.com/goplus/llgo/internal/runtime.SliceLen"(%"github.com/goplus/llgo/internal/runtime.Slice")
|
declare void @"github.com/goplus/llgo/internal/runtime.Panic"(%"github.com/goplus/llgo/internal/runtime.eface")
|
||||||
|
|
||||||
declare ptr @"github.com/goplus/llgo/internal/runtime.SliceData"(%"github.com/goplus/llgo/internal/runtime.Slice")
|
|
||||||
|
|
||||||
declare i64 @"github.com/goplus/llgo/internal/runtime.I2Int"(%"github.com/goplus/llgo/internal/runtime.iface", ptr)
|
|
||||||
|
|
||||||
declare i32 @printf(ptr, ...)
|
declare i32 @printf(ptr, ...)
|
||||||
|
|||||||
@@ -20,7 +20,7 @@ _llgo_2: ; preds = %_llgo_1, %_llgo_0
|
|||||||
ret void
|
ret void
|
||||||
}
|
}
|
||||||
|
|
||||||
define void @main(i32 %0, ptr %1) {
|
define i32 @main(i32 %0, ptr %1) {
|
||||||
_llgo_0:
|
_llgo_0:
|
||||||
store i32 %0, ptr @__llgo_argc, align 4
|
store i32 %0, ptr @__llgo_argc, align 4
|
||||||
store ptr %1, ptr @__llgo_argv, align 8
|
store ptr %1, ptr @__llgo_argv, align 8
|
||||||
@@ -30,7 +30,7 @@ _llgo_0:
|
|||||||
%3 = add i64 %2, 1
|
%3 = add i64 %2, 1
|
||||||
store i64 %3, ptr @main.a, align 4
|
store i64 %3, ptr @main.a, align 4
|
||||||
%4 = load i64, ptr @main.a, align 4
|
%4 = load i64, ptr @main.a, align 4
|
||||||
ret void
|
ret i32 0
|
||||||
}
|
}
|
||||||
|
|
||||||
declare void @"github.com/goplus/llgo/internal/runtime.init"()
|
declare void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
|
|||||||
16
cl/_testdefer/firstloop1/in.go
Normal file
16
cl/_testdefer/firstloop1/in.go
Normal file
@@ -0,0 +1,16 @@
|
|||||||
|
package foo
|
||||||
|
|
||||||
|
func f(s string) bool {
|
||||||
|
return len(s) > 2
|
||||||
|
}
|
||||||
|
|
||||||
|
func Loop() {
|
||||||
|
for i := 0; i < 3; i++ {
|
||||||
|
if s := "hello"; f(s) {
|
||||||
|
defer println(s)
|
||||||
|
} else {
|
||||||
|
defer println("world")
|
||||||
|
return
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
7
cl/_testdefer/firstloop1/out.txt
Normal file
7
cl/_testdefer/firstloop1/out.txt
Normal file
@@ -0,0 +1,7 @@
|
|||||||
|
0: always
|
||||||
|
6: cond
|
||||||
|
3: loop
|
||||||
|
1: loop
|
||||||
|
4: loop
|
||||||
|
2: cond
|
||||||
|
5: cond
|
||||||
7
cl/_testdefer/firstloop2/in.go
Normal file
7
cl/_testdefer/firstloop2/in.go
Normal file
@@ -0,0 +1,7 @@
|
|||||||
|
package foo
|
||||||
|
|
||||||
|
func Loop() {
|
||||||
|
for i := 0; i < 3; i++ {
|
||||||
|
println(i)
|
||||||
|
}
|
||||||
|
}
|
||||||
4
cl/_testdefer/firstloop2/out.txt
Normal file
4
cl/_testdefer/firstloop2/out.txt
Normal file
@@ -0,0 +1,4 @@
|
|||||||
|
0: always
|
||||||
|
3: loop
|
||||||
|
1: loop
|
||||||
|
2: always
|
||||||
20
cl/_testdefer/loop/in.go
Normal file
20
cl/_testdefer/loop/in.go
Normal file
@@ -0,0 +1,20 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
func f(s string) bool {
|
||||||
|
return len(s) > 2
|
||||||
|
}
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
defer func() {
|
||||||
|
println("hi")
|
||||||
|
}()
|
||||||
|
for i := 0; i < 3; i++ {
|
||||||
|
if s := "hello"; f(s) {
|
||||||
|
defer println(s)
|
||||||
|
} else {
|
||||||
|
defer println("world")
|
||||||
|
return
|
||||||
|
}
|
||||||
|
}
|
||||||
|
defer println("bye")
|
||||||
|
}
|
||||||
7
cl/_testdefer/loop/out.txt
Normal file
7
cl/_testdefer/loop/out.txt
Normal file
@@ -0,0 +1,7 @@
|
|||||||
|
0: always
|
||||||
|
1: cond
|
||||||
|
4: loop
|
||||||
|
2: loop
|
||||||
|
5: loop
|
||||||
|
3: cond
|
||||||
|
6: cond
|
||||||
18
cl/_testdefer/multiret/in.go
Normal file
18
cl/_testdefer/multiret/in.go
Normal file
@@ -0,0 +1,18 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
func f(s string) bool {
|
||||||
|
return len(s) > 2
|
||||||
|
}
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
defer func() {
|
||||||
|
println("hi")
|
||||||
|
}()
|
||||||
|
if s := "hello"; f(s) {
|
||||||
|
defer println(s)
|
||||||
|
} else {
|
||||||
|
defer println("world")
|
||||||
|
return
|
||||||
|
}
|
||||||
|
defer println("bye")
|
||||||
|
}
|
||||||
4
cl/_testdefer/multiret/out.txt
Normal file
4
cl/_testdefer/multiret/out.txt
Normal file
@@ -0,0 +1,4 @@
|
|||||||
|
0: always
|
||||||
|
1: cond
|
||||||
|
2: cond
|
||||||
|
3: cond
|
||||||
52
cl/_testdefer/print/in.go
Normal file
52
cl/_testdefer/print/in.go
Normal file
@@ -0,0 +1,52 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
func f() float64 {
|
||||||
|
return 1.0
|
||||||
|
}
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
var v = f()
|
||||||
|
const n = 7 // digits printed
|
||||||
|
var buf [n + 7]byte
|
||||||
|
buf[0] = '+'
|
||||||
|
e := 0 // exp
|
||||||
|
if v == 0 {
|
||||||
|
if 1/v < 0 {
|
||||||
|
buf[0] = '-'
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if v < 0 {
|
||||||
|
v = -v
|
||||||
|
buf[0] = '-'
|
||||||
|
}
|
||||||
|
|
||||||
|
// normalize
|
||||||
|
for v >= 10 {
|
||||||
|
e++
|
||||||
|
v /= 10
|
||||||
|
}
|
||||||
|
for v < 1 {
|
||||||
|
e--
|
||||||
|
v *= 10
|
||||||
|
}
|
||||||
|
|
||||||
|
// round
|
||||||
|
h := 5.0
|
||||||
|
for i := 0; i < n; i++ {
|
||||||
|
h /= 10
|
||||||
|
}
|
||||||
|
v += h
|
||||||
|
if v >= 10 {
|
||||||
|
e++
|
||||||
|
v /= 10
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// format +d.dddd+edd
|
||||||
|
for i := 0; i < n; i++ {
|
||||||
|
s := int(v)
|
||||||
|
buf[i+2] = byte(s + '0')
|
||||||
|
v -= float64(s)
|
||||||
|
v *= 10
|
||||||
|
}
|
||||||
|
}
|
||||||
18
cl/_testdefer/print/out.txt
Normal file
18
cl/_testdefer/print/out.txt
Normal file
@@ -0,0 +1,18 @@
|
|||||||
|
0: always
|
||||||
|
1: cond
|
||||||
|
3: cond
|
||||||
|
4: cond
|
||||||
|
5: cond
|
||||||
|
7: loop
|
||||||
|
6: loop
|
||||||
|
10: loop
|
||||||
|
8: loop
|
||||||
|
9: cond
|
||||||
|
13: loop
|
||||||
|
11: loop
|
||||||
|
12: cond
|
||||||
|
14: cond
|
||||||
|
2: cond
|
||||||
|
17: loop
|
||||||
|
15: loop
|
||||||
|
16: always
|
||||||
17
cl/_testdefer/singleret/in.go
Normal file
17
cl/_testdefer/singleret/in.go
Normal file
@@ -0,0 +1,17 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
func f(s string) bool {
|
||||||
|
return len(s) > 2
|
||||||
|
}
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
defer func() {
|
||||||
|
println("hi")
|
||||||
|
}()
|
||||||
|
if s := "hello"; f(s) {
|
||||||
|
defer println(s)
|
||||||
|
} else {
|
||||||
|
defer println("world")
|
||||||
|
}
|
||||||
|
defer println("bye")
|
||||||
|
}
|
||||||
5
cl/_testdefer/singleret/out.txt
Normal file
5
cl/_testdefer/singleret/out.txt
Normal file
@@ -0,0 +1,5 @@
|
|||||||
|
0: always
|
||||||
|
1: cond
|
||||||
|
2: cond
|
||||||
|
4: cond
|
||||||
|
3: always
|
||||||
18
cl/_testgo/defer1/in.go
Normal file
18
cl/_testgo/defer1/in.go
Normal file
@@ -0,0 +1,18 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
func f(s string) bool {
|
||||||
|
return len(s) > 2
|
||||||
|
}
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
defer func() {
|
||||||
|
println("hi")
|
||||||
|
}()
|
||||||
|
if s := "hello"; f(s) {
|
||||||
|
defer println(s)
|
||||||
|
} else {
|
||||||
|
defer println("world")
|
||||||
|
return
|
||||||
|
}
|
||||||
|
defer println("bye")
|
||||||
|
}
|
||||||
1
cl/_testgo/defer1/out.ll
Normal file
1
cl/_testgo/defer1/out.ll
Normal file
@@ -0,0 +1 @@
|
|||||||
|
;
|
||||||
15
cl/_testgo/defer2/in.go
Normal file
15
cl/_testgo/defer2/in.go
Normal file
@@ -0,0 +1,15 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
func f(s string) bool {
|
||||||
|
return len(s) > 2
|
||||||
|
}
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
if s := "hello"; f(s) {
|
||||||
|
defer println(s)
|
||||||
|
} else {
|
||||||
|
defer println("world")
|
||||||
|
return
|
||||||
|
}
|
||||||
|
defer println("bye")
|
||||||
|
}
|
||||||
1
cl/_testgo/defer2/out.ll
Normal file
1
cl/_testgo/defer2/out.ll
Normal file
@@ -0,0 +1 @@
|
|||||||
|
;
|
||||||
23
cl/_testgo/defer3/in.go
Normal file
23
cl/_testgo/defer3/in.go
Normal file
@@ -0,0 +1,23 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
func f(s string) bool {
|
||||||
|
return len(s) > 2
|
||||||
|
}
|
||||||
|
|
||||||
|
func fail() {
|
||||||
|
defer println("bye")
|
||||||
|
panic("panic message")
|
||||||
|
}
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
defer func() {
|
||||||
|
println("hi")
|
||||||
|
}()
|
||||||
|
if s := "hello"; f(s) {
|
||||||
|
defer println(s)
|
||||||
|
} else {
|
||||||
|
defer println("world")
|
||||||
|
return
|
||||||
|
}
|
||||||
|
fail()
|
||||||
|
}
|
||||||
1
cl/_testgo/defer3/out.ll
Normal file
1
cl/_testgo/defer3/out.ll
Normal file
@@ -0,0 +1 @@
|
|||||||
|
;
|
||||||
22
cl/_testgo/errors/in.go
Normal file
22
cl/_testgo/errors/in.go
Normal file
@@ -0,0 +1,22 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
// New returns an error that formats as the given text.
|
||||||
|
// Each call to New returns a distinct error value even if the text is identical.
|
||||||
|
func New(text string) error {
|
||||||
|
return &errorString{text}
|
||||||
|
}
|
||||||
|
|
||||||
|
// errorString is a trivial implementation of error.
|
||||||
|
type errorString struct {
|
||||||
|
s string
|
||||||
|
}
|
||||||
|
|
||||||
|
func (e *errorString) Error() string {
|
||||||
|
return e.s
|
||||||
|
}
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
err := New("an error")
|
||||||
|
println(err)
|
||||||
|
println(err.Error())
|
||||||
|
}
|
||||||
305
cl/_testgo/errors/out.ll
Normal file
305
cl/_testgo/errors/out.ll
Normal file
@@ -0,0 +1,305 @@
|
|||||||
|
; ModuleID = 'main'
|
||||||
|
source_filename = "main"
|
||||||
|
|
||||||
|
%"github.com/goplus/llgo/internal/runtime.iface" = type { ptr, ptr }
|
||||||
|
%"github.com/goplus/llgo/internal/runtime.String" = type { ptr, i64 }
|
||||||
|
%main.errorString = type { %"github.com/goplus/llgo/internal/runtime.String" }
|
||||||
|
%"github.com/goplus/llgo/internal/abi.StructField" = type { %"github.com/goplus/llgo/internal/runtime.String", ptr, i64, %"github.com/goplus/llgo/internal/runtime.String", i1 }
|
||||||
|
%"github.com/goplus/llgo/internal/runtime.Slice" = type { ptr, i64, i64 }
|
||||||
|
%"github.com/goplus/llgo/internal/abi.Method" = type { %"github.com/goplus/llgo/internal/runtime.String", ptr, ptr, ptr }
|
||||||
|
%"github.com/goplus/llgo/internal/abi.Imethod" = type { %"github.com/goplus/llgo/internal/runtime.String", ptr }
|
||||||
|
|
||||||
|
@"main.init$guard" = global ptr null
|
||||||
|
@"*_llgo_main.errorString" = global ptr null
|
||||||
|
@_llgo_main.errorString = global ptr null
|
||||||
|
@"main.struct$QTufDJA9wEDzuzgkA-ZSrLqW-B6lWN8O25mTSglAoLQ" = global ptr null
|
||||||
|
@_llgo_string = linkonce global ptr null
|
||||||
|
@0 = private unnamed_addr constant [2 x i8] c"s\00", align 1
|
||||||
|
@1 = private unnamed_addr constant [1 x i8] zeroinitializer, align 1
|
||||||
|
@2 = private unnamed_addr constant [5 x i8] c"main\00", align 1
|
||||||
|
@3 = private unnamed_addr constant [6 x i8] c"Error\00", align 1
|
||||||
|
@"_llgo_func$zNDVRsWTIpUPKouNUS805RGX--IV9qVK8B31IZbg5to" = linkonce global ptr null
|
||||||
|
@4 = private unnamed_addr constant [5 x i8] c"main\00", align 1
|
||||||
|
@5 = private unnamed_addr constant [17 x i8] c"main.errorString\00", align 1
|
||||||
|
@"_llgo_iface$Fh8eUJ-Gw4e6TYuajcFIOSCuqSPKAt5nS4ow7xeGXEU" = linkonce global ptr null
|
||||||
|
@6 = private unnamed_addr constant [6 x i8] c"Error\00", align 1
|
||||||
|
@7 = private unnamed_addr constant [5 x i8] c"main\00", align 1
|
||||||
|
@8 = private unnamed_addr constant [1 x i8] zeroinitializer, align 1
|
||||||
|
@__llgo_argc = global ptr null
|
||||||
|
@__llgo_argv = global ptr null
|
||||||
|
@9 = private unnamed_addr constant [9 x i8] c"an error\00", align 1
|
||||||
|
|
||||||
|
define %"github.com/goplus/llgo/internal/runtime.iface" @main.New(%"github.com/goplus/llgo/internal/runtime.String" %0) {
|
||||||
|
_llgo_0:
|
||||||
|
%1 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocZ"(i64 16)
|
||||||
|
%2 = getelementptr inbounds %main.errorString, ptr %1, i32 0, i32 0
|
||||||
|
store %"github.com/goplus/llgo/internal/runtime.String" %0, ptr %2, align 8
|
||||||
|
%3 = load ptr, ptr @"*_llgo_main.errorString", align 8
|
||||||
|
%4 = load ptr, ptr @"_llgo_iface$Fh8eUJ-Gw4e6TYuajcFIOSCuqSPKAt5nS4ow7xeGXEU", align 8
|
||||||
|
%5 = call ptr @"github.com/goplus/llgo/internal/runtime.NewItab"(ptr %4, ptr %3)
|
||||||
|
%6 = alloca %"github.com/goplus/llgo/internal/runtime.iface", align 8
|
||||||
|
%7 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.iface", ptr %6, i32 0, i32 0
|
||||||
|
store ptr %5, ptr %7, align 8
|
||||||
|
%8 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.iface", ptr %6, i32 0, i32 1
|
||||||
|
store ptr %1, ptr %8, align 8
|
||||||
|
%9 = load %"github.com/goplus/llgo/internal/runtime.iface", ptr %6, align 8
|
||||||
|
ret %"github.com/goplus/llgo/internal/runtime.iface" %9
|
||||||
|
}
|
||||||
|
|
||||||
|
define %"github.com/goplus/llgo/internal/runtime.String" @"main.(*errorString).Error"(ptr %0) {
|
||||||
|
_llgo_0:
|
||||||
|
%1 = getelementptr inbounds %main.errorString, ptr %0, i32 0, i32 0
|
||||||
|
%2 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %1, align 8
|
||||||
|
ret %"github.com/goplus/llgo/internal/runtime.String" %2
|
||||||
|
}
|
||||||
|
|
||||||
|
define void @main.init() {
|
||||||
|
_llgo_0:
|
||||||
|
%0 = load i1, ptr @"main.init$guard", align 1
|
||||||
|
br i1 %0, label %_llgo_2, label %_llgo_1
|
||||||
|
|
||||||
|
_llgo_1: ; preds = %_llgo_0
|
||||||
|
store i1 true, ptr @"main.init$guard", align 1
|
||||||
|
call void @"main.init$after"()
|
||||||
|
br label %_llgo_2
|
||||||
|
|
||||||
|
_llgo_2: ; preds = %_llgo_1, %_llgo_0
|
||||||
|
ret void
|
||||||
|
}
|
||||||
|
|
||||||
|
define i32 @main(i32 %0, ptr %1) {
|
||||||
|
_llgo_0:
|
||||||
|
store i32 %0, ptr @__llgo_argc, align 4
|
||||||
|
store ptr %1, ptr @__llgo_argv, align 8
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
|
call void @main.init()
|
||||||
|
%2 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%3 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %2, i32 0, i32 0
|
||||||
|
store ptr @9, ptr %3, align 8
|
||||||
|
%4 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %2, i32 0, i32 1
|
||||||
|
store i64 8, ptr %4, align 4
|
||||||
|
%5 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %2, align 8
|
||||||
|
%6 = call %"github.com/goplus/llgo/internal/runtime.iface" @main.New(%"github.com/goplus/llgo/internal/runtime.String" %5)
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintIface"(%"github.com/goplus/llgo/internal/runtime.iface" %6)
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintByte"(i8 10)
|
||||||
|
%7 = call ptr @"github.com/goplus/llgo/internal/runtime.IfacePtrData"(%"github.com/goplus/llgo/internal/runtime.iface" %6)
|
||||||
|
%8 = extractvalue %"github.com/goplus/llgo/internal/runtime.iface" %6, 0
|
||||||
|
%9 = getelementptr ptr, ptr %8, i64 3
|
||||||
|
%10 = load ptr, ptr %9, align 8
|
||||||
|
%11 = alloca { ptr, ptr }, align 8
|
||||||
|
%12 = getelementptr inbounds { ptr, ptr }, ptr %11, i32 0, i32 0
|
||||||
|
store ptr %10, ptr %12, align 8
|
||||||
|
%13 = getelementptr inbounds { ptr, ptr }, ptr %11, i32 0, i32 1
|
||||||
|
store ptr %7, ptr %13, align 8
|
||||||
|
%14 = load { ptr, ptr }, ptr %11, align 8
|
||||||
|
%15 = extractvalue { ptr, ptr } %14, 1
|
||||||
|
%16 = extractvalue { ptr, ptr } %14, 0
|
||||||
|
%17 = call %"github.com/goplus/llgo/internal/runtime.String" %16(ptr %15)
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintString"(%"github.com/goplus/llgo/internal/runtime.String" %17)
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintByte"(i8 10)
|
||||||
|
ret i32 0
|
||||||
|
}
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.AllocZ"(i64)
|
||||||
|
|
||||||
|
define void @"main.init$after"() {
|
||||||
|
_llgo_0:
|
||||||
|
%0 = call ptr @"github.com/goplus/llgo/internal/runtime.NewNamed"(i64 25, i64 0, i64 1)
|
||||||
|
store ptr %0, ptr @_llgo_main.errorString, align 8
|
||||||
|
%1 = load ptr, ptr @_llgo_string, align 8
|
||||||
|
%2 = icmp eq ptr %1, null
|
||||||
|
br i1 %2, label %_llgo_1, label %_llgo_2
|
||||||
|
|
||||||
|
_llgo_1: ; preds = %_llgo_0
|
||||||
|
%3 = call ptr @"github.com/goplus/llgo/internal/runtime.Basic"(i64 24)
|
||||||
|
store ptr %3, ptr @_llgo_string, align 8
|
||||||
|
br label %_llgo_2
|
||||||
|
|
||||||
|
_llgo_2: ; preds = %_llgo_1, %_llgo_0
|
||||||
|
%4 = load ptr, ptr @_llgo_string, align 8
|
||||||
|
%5 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%6 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %5, i32 0, i32 0
|
||||||
|
store ptr @0, ptr %6, align 8
|
||||||
|
%7 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %5, i32 0, i32 1
|
||||||
|
store i64 1, ptr %7, align 4
|
||||||
|
%8 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %5, align 8
|
||||||
|
%9 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%10 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %9, i32 0, i32 0
|
||||||
|
store ptr @1, ptr %10, align 8
|
||||||
|
%11 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %9, i32 0, i32 1
|
||||||
|
store i64 0, ptr %11, align 4
|
||||||
|
%12 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %9, align 8
|
||||||
|
%13 = call %"github.com/goplus/llgo/internal/abi.StructField" @"github.com/goplus/llgo/internal/runtime.StructField"(%"github.com/goplus/llgo/internal/runtime.String" %8, ptr %4, i64 0, %"github.com/goplus/llgo/internal/runtime.String" %12, i1 false)
|
||||||
|
%14 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%15 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %14, i32 0, i32 0
|
||||||
|
store ptr @2, ptr %15, align 8
|
||||||
|
%16 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %14, i32 0, i32 1
|
||||||
|
store i64 4, ptr %16, align 4
|
||||||
|
%17 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %14, align 8
|
||||||
|
%18 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocU"(i64 56)
|
||||||
|
%19 = getelementptr %"github.com/goplus/llgo/internal/abi.StructField", ptr %18, i64 0
|
||||||
|
store %"github.com/goplus/llgo/internal/abi.StructField" %13, ptr %19, align 8
|
||||||
|
%20 = alloca %"github.com/goplus/llgo/internal/runtime.Slice", align 8
|
||||||
|
%21 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %20, i32 0, i32 0
|
||||||
|
store ptr %18, ptr %21, align 8
|
||||||
|
%22 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %20, i32 0, i32 1
|
||||||
|
store i64 1, ptr %22, align 4
|
||||||
|
%23 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %20, i32 0, i32 2
|
||||||
|
store i64 1, ptr %23, align 4
|
||||||
|
%24 = load %"github.com/goplus/llgo/internal/runtime.Slice", ptr %20, align 8
|
||||||
|
%25 = call ptr @"github.com/goplus/llgo/internal/runtime.Struct"(%"github.com/goplus/llgo/internal/runtime.String" %17, i64 16, %"github.com/goplus/llgo/internal/runtime.Slice" %24)
|
||||||
|
store ptr %25, ptr @"main.struct$QTufDJA9wEDzuzgkA-ZSrLqW-B6lWN8O25mTSglAoLQ", align 8
|
||||||
|
%26 = load ptr, ptr @"main.struct$QTufDJA9wEDzuzgkA-ZSrLqW-B6lWN8O25mTSglAoLQ", align 8
|
||||||
|
%27 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%28 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %27, i32 0, i32 0
|
||||||
|
store ptr @3, ptr %28, align 8
|
||||||
|
%29 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %27, i32 0, i32 1
|
||||||
|
store i64 5, ptr %29, align 4
|
||||||
|
%30 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %27, align 8
|
||||||
|
%31 = load ptr, ptr @_llgo_string, align 8
|
||||||
|
%32 = load ptr, ptr @"_llgo_func$zNDVRsWTIpUPKouNUS805RGX--IV9qVK8B31IZbg5to", align 8
|
||||||
|
%33 = icmp eq ptr %32, null
|
||||||
|
br i1 %33, label %_llgo_3, label %_llgo_4
|
||||||
|
|
||||||
|
_llgo_3: ; preds = %_llgo_2
|
||||||
|
%34 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocU"(i64 0)
|
||||||
|
%35 = alloca %"github.com/goplus/llgo/internal/runtime.Slice", align 8
|
||||||
|
%36 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %35, i32 0, i32 0
|
||||||
|
store ptr %34, ptr %36, align 8
|
||||||
|
%37 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %35, i32 0, i32 1
|
||||||
|
store i64 0, ptr %37, align 4
|
||||||
|
%38 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %35, i32 0, i32 2
|
||||||
|
store i64 0, ptr %38, align 4
|
||||||
|
%39 = load %"github.com/goplus/llgo/internal/runtime.Slice", ptr %35, align 8
|
||||||
|
%40 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocU"(i64 8)
|
||||||
|
%41 = getelementptr ptr, ptr %40, i64 0
|
||||||
|
store ptr %31, ptr %41, align 8
|
||||||
|
%42 = alloca %"github.com/goplus/llgo/internal/runtime.Slice", align 8
|
||||||
|
%43 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %42, i32 0, i32 0
|
||||||
|
store ptr %40, ptr %43, align 8
|
||||||
|
%44 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %42, i32 0, i32 1
|
||||||
|
store i64 1, ptr %44, align 4
|
||||||
|
%45 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %42, i32 0, i32 2
|
||||||
|
store i64 1, ptr %45, align 4
|
||||||
|
%46 = load %"github.com/goplus/llgo/internal/runtime.Slice", ptr %42, align 8
|
||||||
|
%47 = call ptr @"github.com/goplus/llgo/internal/runtime.Func"(%"github.com/goplus/llgo/internal/runtime.Slice" %39, %"github.com/goplus/llgo/internal/runtime.Slice" %46, i1 false)
|
||||||
|
store ptr %47, ptr @"_llgo_func$zNDVRsWTIpUPKouNUS805RGX--IV9qVK8B31IZbg5to", align 8
|
||||||
|
br label %_llgo_4
|
||||||
|
|
||||||
|
_llgo_4: ; preds = %_llgo_3, %_llgo_2
|
||||||
|
%48 = load ptr, ptr @"_llgo_func$zNDVRsWTIpUPKouNUS805RGX--IV9qVK8B31IZbg5to", align 8
|
||||||
|
%49 = alloca %"github.com/goplus/llgo/internal/abi.Method", align 8
|
||||||
|
%50 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %49, i32 0, i32 0
|
||||||
|
store %"github.com/goplus/llgo/internal/runtime.String" %30, ptr %50, align 8
|
||||||
|
%51 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %49, i32 0, i32 1
|
||||||
|
store ptr %48, ptr %51, align 8
|
||||||
|
%52 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %49, i32 0, i32 2
|
||||||
|
store ptr @"main.(*errorString).Error", ptr %52, align 8
|
||||||
|
%53 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %49, i32 0, i32 3
|
||||||
|
store ptr @"main.(*errorString).Error", ptr %53, align 8
|
||||||
|
%54 = load %"github.com/goplus/llgo/internal/abi.Method", ptr %49, align 8
|
||||||
|
%55 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocU"(i64 40)
|
||||||
|
%56 = getelementptr %"github.com/goplus/llgo/internal/abi.Method", ptr %55, i64 0
|
||||||
|
store %"github.com/goplus/llgo/internal/abi.Method" %54, ptr %56, align 8
|
||||||
|
%57 = alloca %"github.com/goplus/llgo/internal/runtime.Slice", align 8
|
||||||
|
%58 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %57, i32 0, i32 0
|
||||||
|
store ptr %55, ptr %58, align 8
|
||||||
|
%59 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %57, i32 0, i32 1
|
||||||
|
store i64 1, ptr %59, align 4
|
||||||
|
%60 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %57, i32 0, i32 2
|
||||||
|
store i64 1, ptr %60, align 4
|
||||||
|
%61 = load %"github.com/goplus/llgo/internal/runtime.Slice", ptr %57, align 8
|
||||||
|
%62 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%63 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %62, i32 0, i32 0
|
||||||
|
store ptr @4, ptr %63, align 8
|
||||||
|
%64 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %62, i32 0, i32 1
|
||||||
|
store i64 4, ptr %64, align 4
|
||||||
|
%65 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %62, align 8
|
||||||
|
%66 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%67 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %66, i32 0, i32 0
|
||||||
|
store ptr @5, ptr %67, align 8
|
||||||
|
%68 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %66, i32 0, i32 1
|
||||||
|
store i64 16, ptr %68, align 4
|
||||||
|
%69 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %66, align 8
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.InitNamed"(ptr %0, %"github.com/goplus/llgo/internal/runtime.String" %65, %"github.com/goplus/llgo/internal/runtime.String" %69, ptr %26, { ptr, i64, i64 } zeroinitializer, %"github.com/goplus/llgo/internal/runtime.Slice" %61)
|
||||||
|
%70 = load ptr, ptr @_llgo_main.errorString, align 8
|
||||||
|
%71 = call ptr @"github.com/goplus/llgo/internal/runtime.PointerTo"(ptr %70)
|
||||||
|
store ptr %71, ptr @"*_llgo_main.errorString", align 8
|
||||||
|
%72 = load ptr, ptr @"_llgo_func$zNDVRsWTIpUPKouNUS805RGX--IV9qVK8B31IZbg5to", align 8
|
||||||
|
%73 = load ptr, ptr @"_llgo_iface$Fh8eUJ-Gw4e6TYuajcFIOSCuqSPKAt5nS4ow7xeGXEU", align 8
|
||||||
|
%74 = icmp eq ptr %73, null
|
||||||
|
br i1 %74, label %_llgo_5, label %_llgo_6
|
||||||
|
|
||||||
|
_llgo_5: ; preds = %_llgo_4
|
||||||
|
%75 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%76 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %75, i32 0, i32 0
|
||||||
|
store ptr @6, ptr %76, align 8
|
||||||
|
%77 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %75, i32 0, i32 1
|
||||||
|
store i64 5, ptr %77, align 4
|
||||||
|
%78 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %75, align 8
|
||||||
|
%79 = alloca %"github.com/goplus/llgo/internal/abi.Imethod", align 8
|
||||||
|
%80 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Imethod", ptr %79, i32 0, i32 0
|
||||||
|
store %"github.com/goplus/llgo/internal/runtime.String" %78, ptr %80, align 8
|
||||||
|
%81 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Imethod", ptr %79, i32 0, i32 1
|
||||||
|
store ptr %72, ptr %81, align 8
|
||||||
|
%82 = load %"github.com/goplus/llgo/internal/abi.Imethod", ptr %79, align 8
|
||||||
|
%83 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocU"(i64 24)
|
||||||
|
%84 = getelementptr %"github.com/goplus/llgo/internal/abi.Imethod", ptr %83, i64 0
|
||||||
|
store %"github.com/goplus/llgo/internal/abi.Imethod" %82, ptr %84, align 8
|
||||||
|
%85 = alloca %"github.com/goplus/llgo/internal/runtime.Slice", align 8
|
||||||
|
%86 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %85, i32 0, i32 0
|
||||||
|
store ptr %83, ptr %86, align 8
|
||||||
|
%87 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %85, i32 0, i32 1
|
||||||
|
store i64 1, ptr %87, align 4
|
||||||
|
%88 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %85, i32 0, i32 2
|
||||||
|
store i64 1, ptr %88, align 4
|
||||||
|
%89 = load %"github.com/goplus/llgo/internal/runtime.Slice", ptr %85, align 8
|
||||||
|
%90 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%91 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %90, i32 0, i32 0
|
||||||
|
store ptr @7, ptr %91, align 8
|
||||||
|
%92 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %90, i32 0, i32 1
|
||||||
|
store i64 4, ptr %92, align 4
|
||||||
|
%93 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %90, align 8
|
||||||
|
%94 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%95 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %94, i32 0, i32 0
|
||||||
|
store ptr @8, ptr %95, align 8
|
||||||
|
%96 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %94, i32 0, i32 1
|
||||||
|
store i64 0, ptr %96, align 4
|
||||||
|
%97 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %94, align 8
|
||||||
|
%98 = call ptr @"github.com/goplus/llgo/internal/runtime.Interface"(%"github.com/goplus/llgo/internal/runtime.String" %93, %"github.com/goplus/llgo/internal/runtime.String" %97, %"github.com/goplus/llgo/internal/runtime.Slice" %89)
|
||||||
|
store ptr %98, ptr @"_llgo_iface$Fh8eUJ-Gw4e6TYuajcFIOSCuqSPKAt5nS4ow7xeGXEU", align 8
|
||||||
|
br label %_llgo_6
|
||||||
|
|
||||||
|
_llgo_6: ; preds = %_llgo_5, %_llgo_4
|
||||||
|
ret void
|
||||||
|
}
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.NewNamed"(i64, i64, i64)
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.Basic"(i64)
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.Struct"(%"github.com/goplus/llgo/internal/runtime.String", i64, %"github.com/goplus/llgo/internal/runtime.Slice")
|
||||||
|
|
||||||
|
declare %"github.com/goplus/llgo/internal/abi.StructField" @"github.com/goplus/llgo/internal/runtime.StructField"(%"github.com/goplus/llgo/internal/runtime.String", ptr, i64, %"github.com/goplus/llgo/internal/runtime.String", i1)
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.AllocU"(i64)
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.InitNamed"(ptr, %"github.com/goplus/llgo/internal/runtime.String", %"github.com/goplus/llgo/internal/runtime.String", ptr, %"github.com/goplus/llgo/internal/runtime.Slice", %"github.com/goplus/llgo/internal/runtime.Slice")
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.Func"(%"github.com/goplus/llgo/internal/runtime.Slice", %"github.com/goplus/llgo/internal/runtime.Slice", i1)
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.PointerTo"(ptr)
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.Interface"(%"github.com/goplus/llgo/internal/runtime.String", %"github.com/goplus/llgo/internal/runtime.String", %"github.com/goplus/llgo/internal/runtime.Slice")
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.NewItab"(ptr, ptr)
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.PrintIface"(%"github.com/goplus/llgo/internal/runtime.iface")
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.PrintByte"(i8)
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.IfacePtrData"(%"github.com/goplus/llgo/internal/runtime.iface")
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.PrintString"(%"github.com/goplus/llgo/internal/runtime.String")
|
||||||
12
cl/_testgo/goroutine/in.go
Normal file
12
cl/_testgo/goroutine/in.go
Normal file
@@ -0,0 +1,12 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
done := false
|
||||||
|
go func(s string) {
|
||||||
|
println(s)
|
||||||
|
done = true
|
||||||
|
}("Hello, goroutine")
|
||||||
|
for !done {
|
||||||
|
print(".")
|
||||||
|
}
|
||||||
|
}
|
||||||
111
cl/_testgo/goroutine/out.ll
Normal file
111
cl/_testgo/goroutine/out.ll
Normal file
@@ -0,0 +1,111 @@
|
|||||||
|
; ModuleID = 'main'
|
||||||
|
source_filename = "main"
|
||||||
|
|
||||||
|
%"github.com/goplus/llgo/internal/runtime.String" = type { ptr, i64 }
|
||||||
|
|
||||||
|
@"main.init$guard" = global ptr null
|
||||||
|
@__llgo_argc = global ptr null
|
||||||
|
@__llgo_argv = global ptr null
|
||||||
|
@0 = private unnamed_addr constant [17 x i8] c"Hello, goroutine\00", align 1
|
||||||
|
@1 = private unnamed_addr constant [2 x i8] c".\00", align 1
|
||||||
|
|
||||||
|
define void @main.init() {
|
||||||
|
_llgo_0:
|
||||||
|
%0 = load i1, ptr @"main.init$guard", align 1
|
||||||
|
br i1 %0, label %_llgo_2, label %_llgo_1
|
||||||
|
|
||||||
|
_llgo_1: ; preds = %_llgo_0
|
||||||
|
store i1 true, ptr @"main.init$guard", align 1
|
||||||
|
br label %_llgo_2
|
||||||
|
|
||||||
|
_llgo_2: ; preds = %_llgo_1, %_llgo_0
|
||||||
|
ret void
|
||||||
|
}
|
||||||
|
|
||||||
|
define i32 @main(i32 %0, ptr %1) {
|
||||||
|
_llgo_0:
|
||||||
|
store i32 %0, ptr @__llgo_argc, align 4
|
||||||
|
store ptr %1, ptr @__llgo_argv, align 8
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
|
call void @main.init()
|
||||||
|
%2 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocZ"(i64 1)
|
||||||
|
store i1 false, ptr %2, align 1
|
||||||
|
%3 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocU"(i64 8)
|
||||||
|
%4 = getelementptr inbounds { ptr }, ptr %3, i32 0, i32 0
|
||||||
|
store ptr %2, ptr %4, align 8
|
||||||
|
%5 = alloca { ptr, ptr }, align 8
|
||||||
|
%6 = getelementptr inbounds { ptr, ptr }, ptr %5, i32 0, i32 0
|
||||||
|
store ptr @"main.main$1", ptr %6, align 8
|
||||||
|
%7 = getelementptr inbounds { ptr, ptr }, ptr %5, i32 0, i32 1
|
||||||
|
store ptr %3, ptr %7, align 8
|
||||||
|
%8 = load { ptr, ptr }, ptr %5, align 8
|
||||||
|
%9 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%10 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %9, i32 0, i32 0
|
||||||
|
store ptr @0, ptr %10, align 8
|
||||||
|
%11 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %9, i32 0, i32 1
|
||||||
|
store i64 16, ptr %11, align 4
|
||||||
|
%12 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %9, align 8
|
||||||
|
%13 = call ptr @malloc(i64 32)
|
||||||
|
%14 = getelementptr inbounds { { ptr, ptr }, %"github.com/goplus/llgo/internal/runtime.String" }, ptr %13, i32 0, i32 0
|
||||||
|
store { ptr, ptr } %8, ptr %14, align 8
|
||||||
|
%15 = getelementptr inbounds { { ptr, ptr }, %"github.com/goplus/llgo/internal/runtime.String" }, ptr %13, i32 0, i32 1
|
||||||
|
store %"github.com/goplus/llgo/internal/runtime.String" %12, ptr %15, align 8
|
||||||
|
%16 = alloca i8, i64 8, align 1
|
||||||
|
%17 = call i32 @pthread_create(ptr %16, ptr null, ptr @"main._llgo_routine$1", ptr %13)
|
||||||
|
br label %_llgo_3
|
||||||
|
|
||||||
|
_llgo_1: ; preds = %_llgo_3
|
||||||
|
%18 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%19 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %18, i32 0, i32 0
|
||||||
|
store ptr @1, ptr %19, align 8
|
||||||
|
%20 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %18, i32 0, i32 1
|
||||||
|
store i64 1, ptr %20, align 4
|
||||||
|
%21 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %18, align 8
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintString"(%"github.com/goplus/llgo/internal/runtime.String" %21)
|
||||||
|
br label %_llgo_3
|
||||||
|
|
||||||
|
_llgo_2: ; preds = %_llgo_3
|
||||||
|
ret i32 0
|
||||||
|
|
||||||
|
_llgo_3: ; preds = %_llgo_1, %_llgo_0
|
||||||
|
%22 = load i1, ptr %2, align 1
|
||||||
|
br i1 %22, label %_llgo_2, label %_llgo_1
|
||||||
|
}
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.AllocZ"(i64)
|
||||||
|
|
||||||
|
define void @"main.main$1"(ptr %0, %"github.com/goplus/llgo/internal/runtime.String" %1) {
|
||||||
|
_llgo_0:
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintString"(%"github.com/goplus/llgo/internal/runtime.String" %1)
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintByte"(i8 10)
|
||||||
|
%2 = load { ptr }, ptr %0, align 8
|
||||||
|
%3 = extractvalue { ptr } %2, 0
|
||||||
|
store i1 true, ptr %3, align 1
|
||||||
|
ret void
|
||||||
|
}
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.AllocU"(i64)
|
||||||
|
|
||||||
|
declare ptr @malloc(i64)
|
||||||
|
|
||||||
|
define ptr @"main._llgo_routine$1"(ptr %0) {
|
||||||
|
_llgo_0:
|
||||||
|
%1 = load { { ptr, ptr }, %"github.com/goplus/llgo/internal/runtime.String" }, ptr %0, align 8
|
||||||
|
%2 = extractvalue { { ptr, ptr }, %"github.com/goplus/llgo/internal/runtime.String" } %1, 0
|
||||||
|
%3 = extractvalue { { ptr, ptr }, %"github.com/goplus/llgo/internal/runtime.String" } %1, 1
|
||||||
|
%4 = extractvalue { ptr, ptr } %2, 1
|
||||||
|
%5 = extractvalue { ptr, ptr } %2, 0
|
||||||
|
call void %5(ptr %4, %"github.com/goplus/llgo/internal/runtime.String" %3)
|
||||||
|
call void @free(ptr %0)
|
||||||
|
ret ptr null
|
||||||
|
}
|
||||||
|
|
||||||
|
declare void @free(ptr)
|
||||||
|
|
||||||
|
declare i32 @pthread_create(ptr, ptr, ptr, ptr)
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.PrintString"(%"github.com/goplus/llgo/internal/runtime.String")
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.PrintByte"(i8)
|
||||||
85
cl/_testgo/ifaceconv/in.go
Normal file
85
cl/_testgo/ifaceconv/in.go
Normal file
@@ -0,0 +1,85 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
// Tests of interface conversions and type assertions.
|
||||||
|
|
||||||
|
type I0 interface {
|
||||||
|
}
|
||||||
|
type I1 interface {
|
||||||
|
f()
|
||||||
|
}
|
||||||
|
type I2 interface {
|
||||||
|
f()
|
||||||
|
g()
|
||||||
|
}
|
||||||
|
|
||||||
|
type C0 struct{}
|
||||||
|
type C1 struct{}
|
||||||
|
|
||||||
|
func (C1) f() {}
|
||||||
|
|
||||||
|
type C2 struct{}
|
||||||
|
|
||||||
|
func (C2) f() {}
|
||||||
|
func (C2) g() {}
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
var i0 I0
|
||||||
|
var i1 I1
|
||||||
|
var i2 I2
|
||||||
|
|
||||||
|
// Nil always causes a type assertion to fail, even to the
|
||||||
|
// same type.
|
||||||
|
if _, ok := i0.(I0); ok {
|
||||||
|
panic("nil i0.(I0) succeeded")
|
||||||
|
}
|
||||||
|
if _, ok := i1.(I1); ok {
|
||||||
|
panic("nil i1.(I1) succeeded")
|
||||||
|
}
|
||||||
|
if _, ok := i2.(I2); ok {
|
||||||
|
panic("nil i2.(I2) succeeded")
|
||||||
|
}
|
||||||
|
|
||||||
|
// Conversions can't fail, even with nil.
|
||||||
|
_ = I0(i0)
|
||||||
|
|
||||||
|
_ = I0(i1)
|
||||||
|
_ = I1(i1)
|
||||||
|
|
||||||
|
_ = I0(i2)
|
||||||
|
_ = I1(i2)
|
||||||
|
_ = I2(i2)
|
||||||
|
|
||||||
|
// Non-nil type assertions pass or fail based on the concrete type.
|
||||||
|
i1 = C1{}
|
||||||
|
if _, ok := i1.(I0); !ok {
|
||||||
|
panic("C1 i1.(I0) failed")
|
||||||
|
}
|
||||||
|
if _, ok := i1.(I1); !ok {
|
||||||
|
panic("C1 i1.(I1) failed")
|
||||||
|
}
|
||||||
|
if _, ok := i1.(I2); ok {
|
||||||
|
panic("C1 i1.(I2) succeeded")
|
||||||
|
}
|
||||||
|
|
||||||
|
i1 = C2{}
|
||||||
|
if _, ok := i1.(I0); !ok {
|
||||||
|
panic("C2 i1.(I0) failed")
|
||||||
|
}
|
||||||
|
if _, ok := i1.(I1); !ok {
|
||||||
|
panic("C2 i1.(I1) failed")
|
||||||
|
}
|
||||||
|
if _, ok := i1.(I2); !ok {
|
||||||
|
panic("C2 i1.(I2) failed")
|
||||||
|
}
|
||||||
|
|
||||||
|
// Conversions can't fail.
|
||||||
|
i1 = C1{}
|
||||||
|
if I0(i1) == nil {
|
||||||
|
panic("C1 I0(i1) was nil")
|
||||||
|
}
|
||||||
|
if I1(i1) == nil {
|
||||||
|
panic("C1 I1(i1) was nil")
|
||||||
|
}
|
||||||
|
|
||||||
|
println("pass")
|
||||||
|
}
|
||||||
1305
cl/_testgo/ifaceconv/out.ll
Normal file
1305
cl/_testgo/ifaceconv/out.ll
Normal file
File diff suppressed because it is too large
Load Diff
60
cl/_testgo/ifaceprom/in.go
Normal file
60
cl/_testgo/ifaceprom/in.go
Normal file
@@ -0,0 +1,60 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
// Test of promotion of methods of an interface embedded within a
|
||||||
|
// struct. In particular, this test exercises that the correct
|
||||||
|
// method is called.
|
||||||
|
|
||||||
|
type I interface {
|
||||||
|
one() int
|
||||||
|
two() string
|
||||||
|
}
|
||||||
|
|
||||||
|
type S struct {
|
||||||
|
I
|
||||||
|
}
|
||||||
|
|
||||||
|
type impl struct{}
|
||||||
|
|
||||||
|
func (impl) one() int {
|
||||||
|
return 1
|
||||||
|
}
|
||||||
|
|
||||||
|
func (impl) two() string {
|
||||||
|
return "two"
|
||||||
|
}
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
var s S
|
||||||
|
s.I = impl{}
|
||||||
|
if one := s.I.one(); one != 1 {
|
||||||
|
panic(one)
|
||||||
|
}
|
||||||
|
if one := s.one(); one != 1 {
|
||||||
|
panic(one)
|
||||||
|
}
|
||||||
|
closOne := s.I.one
|
||||||
|
if one := closOne(); one != 1 {
|
||||||
|
panic(one)
|
||||||
|
}
|
||||||
|
closOne = s.one
|
||||||
|
if one := closOne(); one != 1 {
|
||||||
|
panic(one)
|
||||||
|
}
|
||||||
|
|
||||||
|
if two := s.I.two(); two != "two" {
|
||||||
|
panic(two)
|
||||||
|
}
|
||||||
|
if two := s.two(); two != "two" {
|
||||||
|
panic(two)
|
||||||
|
}
|
||||||
|
closTwo := s.I.two
|
||||||
|
if two := closTwo(); two != "two" {
|
||||||
|
panic(two)
|
||||||
|
}
|
||||||
|
closTwo = s.two
|
||||||
|
if two := closTwo(); two != "two" {
|
||||||
|
panic(two)
|
||||||
|
}
|
||||||
|
|
||||||
|
println("pass")
|
||||||
|
}
|
||||||
1050
cl/_testgo/ifaceprom/out.ll
Normal file
1050
cl/_testgo/ifaceprom/out.ll
Normal file
File diff suppressed because it is too large
Load Diff
27
cl/_testgo/interface/in.go
Normal file
27
cl/_testgo/interface/in.go
Normal file
@@ -0,0 +1,27 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/goplus/llgo/cl/internal/foo"
|
||||||
|
)
|
||||||
|
|
||||||
|
type Game1 struct {
|
||||||
|
*foo.Game
|
||||||
|
}
|
||||||
|
|
||||||
|
type Game2 struct {
|
||||||
|
}
|
||||||
|
|
||||||
|
func (p *Game2) initGame() {
|
||||||
|
}
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
var g1 any = &Game1{&foo.Game{}}
|
||||||
|
var g2 any = &Game2{}
|
||||||
|
v1, ok := g1.(foo.Gamer)
|
||||||
|
println("OK", v1, ok)
|
||||||
|
if ok {
|
||||||
|
v1.Load()
|
||||||
|
}
|
||||||
|
v2, ok := g2.(foo.Gamer)
|
||||||
|
println("FAIL", v2, ok)
|
||||||
|
}
|
||||||
773
cl/_testgo/interface/out.ll
Normal file
773
cl/_testgo/interface/out.ll
Normal file
@@ -0,0 +1,773 @@
|
|||||||
|
; ModuleID = 'main'
|
||||||
|
source_filename = "main"
|
||||||
|
|
||||||
|
%main.Game1 = type { ptr }
|
||||||
|
%"github.com/goplus/llgo/internal/runtime.eface" = type { ptr, ptr }
|
||||||
|
%"github.com/goplus/llgo/internal/runtime.iface" = type { ptr, ptr }
|
||||||
|
%"github.com/goplus/llgo/internal/runtime.String" = type { ptr, i64 }
|
||||||
|
%"github.com/goplus/llgo/internal/runtime.Slice" = type { ptr, i64, i64 }
|
||||||
|
%"github.com/goplus/llgo/internal/abi.Method" = type { %"github.com/goplus/llgo/internal/runtime.String", ptr, ptr, ptr }
|
||||||
|
%"github.com/goplus/llgo/internal/abi.StructField" = type { %"github.com/goplus/llgo/internal/runtime.String", ptr, i64, %"github.com/goplus/llgo/internal/runtime.String", i1 }
|
||||||
|
%"github.com/goplus/llgo/internal/abi.Imethod" = type { %"github.com/goplus/llgo/internal/runtime.String", ptr }
|
||||||
|
|
||||||
|
@"main.init$guard" = global ptr null
|
||||||
|
@__llgo_argc = global ptr null
|
||||||
|
@__llgo_argv = global ptr null
|
||||||
|
@"*_llgo_main.Game1" = linkonce global ptr null
|
||||||
|
@_llgo_main.Game1 = linkonce global ptr null
|
||||||
|
@"_llgo_struct$cJmCzeVn0orHWafCrTGAnbbAF46F2A4Fms4bJBm8ITI" = linkonce global ptr null
|
||||||
|
@"*_llgo_github.com/goplus/llgo/cl/internal/foo.Game" = linkonce global ptr null
|
||||||
|
@"_llgo_github.com/goplus/llgo/cl/internal/foo.Game" = linkonce global ptr null
|
||||||
|
@"_llgo_struct$n1H8J_3prDN3firMwPxBLVTkE5hJ9Di-AqNvaC9jczw" = linkonce global ptr null
|
||||||
|
@0 = private unnamed_addr constant [5 x i8] c"main\00", align 1
|
||||||
|
@1 = private unnamed_addr constant [5 x i8] c"Load\00", align 1
|
||||||
|
@"_llgo_func$2_iS07vIlF2_rZqWB5eU0IvP_9HviM4MYZNkXZDvbac" = linkonce global ptr null
|
||||||
|
@2 = private unnamed_addr constant [9 x i8] c"initGame\00", align 1
|
||||||
|
@3 = private unnamed_addr constant [48 x i8] c"github.com/goplus/llgo/cl/internal/foo.initGame\00", align 1
|
||||||
|
@4 = private unnamed_addr constant [39 x i8] c"github.com/goplus/llgo/cl/internal/foo\00", align 1
|
||||||
|
@5 = private unnamed_addr constant [44 x i8] c"github.com/goplus/llgo/cl/internal/foo.Game\00", align 1
|
||||||
|
@6 = private unnamed_addr constant [5 x i8] c"Game\00", align 1
|
||||||
|
@7 = private unnamed_addr constant [1 x i8] zeroinitializer, align 1
|
||||||
|
@8 = private unnamed_addr constant [5 x i8] c"main\00", align 1
|
||||||
|
@9 = private unnamed_addr constant [5 x i8] c"Load\00", align 1
|
||||||
|
@10 = private unnamed_addr constant [9 x i8] c"initGame\00", align 1
|
||||||
|
@11 = private unnamed_addr constant [48 x i8] c"github.com/goplus/llgo/cl/internal/foo.initGame\00", align 1
|
||||||
|
@12 = private unnamed_addr constant [5 x i8] c"main\00", align 1
|
||||||
|
@13 = private unnamed_addr constant [11 x i8] c"main.Game1\00", align 1
|
||||||
|
@"*_llgo_main.Game2" = linkonce global ptr null
|
||||||
|
@_llgo_main.Game2 = linkonce global ptr null
|
||||||
|
@14 = private unnamed_addr constant [9 x i8] c"initGame\00", align 1
|
||||||
|
@15 = private unnamed_addr constant [14 x i8] c"main.initGame\00", align 1
|
||||||
|
@16 = private unnamed_addr constant [5 x i8] c"main\00", align 1
|
||||||
|
@17 = private unnamed_addr constant [11 x i8] c"main.Game2\00", align 1
|
||||||
|
@"_llgo_github.com/goplus/llgo/cl/internal/foo.Gamer" = linkonce global ptr null
|
||||||
|
@18 = private unnamed_addr constant [5 x i8] c"Load\00", align 1
|
||||||
|
@19 = private unnamed_addr constant [48 x i8] c"github.com/goplus/llgo/cl/internal/foo.initGame\00", align 1
|
||||||
|
@20 = private unnamed_addr constant [39 x i8] c"github.com/goplus/llgo/cl/internal/foo\00", align 1
|
||||||
|
@21 = private unnamed_addr constant [45 x i8] c"github.com/goplus/llgo/cl/internal/foo.Gamer\00", align 1
|
||||||
|
@"main.iface$sO8a1LvuUsjXwiwaC6sR9-L4DiYgiOnZi7iosyShJXg" = global ptr null
|
||||||
|
@22 = private unnamed_addr constant [5 x i8] c"Load\00", align 1
|
||||||
|
@23 = private unnamed_addr constant [48 x i8] c"github.com/goplus/llgo/cl/internal/foo.initGame\00", align 1
|
||||||
|
@24 = private unnamed_addr constant [5 x i8] c"main\00", align 1
|
||||||
|
@25 = private unnamed_addr constant [1 x i8] zeroinitializer, align 1
|
||||||
|
@26 = private unnamed_addr constant [3 x i8] c"OK\00", align 1
|
||||||
|
@27 = private unnamed_addr constant [5 x i8] c"FAIL\00", align 1
|
||||||
|
|
||||||
|
define void @main.Game1.Load(%main.Game1 %0) {
|
||||||
|
_llgo_0:
|
||||||
|
%1 = alloca %main.Game1, align 8
|
||||||
|
%2 = call ptr @"github.com/goplus/llgo/internal/runtime.Zeroinit"(ptr %1, i64 8)
|
||||||
|
store %main.Game1 %0, ptr %2, align 8
|
||||||
|
%3 = getelementptr inbounds %main.Game1, ptr %2, i32 0, i32 0
|
||||||
|
%4 = load ptr, ptr %3, align 8
|
||||||
|
call void @"github.com/goplus/llgo/cl/internal/foo.(*Game).Load"(ptr %4)
|
||||||
|
ret void
|
||||||
|
}
|
||||||
|
|
||||||
|
define void @main.Game1.initGame(%main.Game1 %0) {
|
||||||
|
_llgo_0:
|
||||||
|
%1 = alloca %main.Game1, align 8
|
||||||
|
%2 = call ptr @"github.com/goplus/llgo/internal/runtime.Zeroinit"(ptr %1, i64 8)
|
||||||
|
store %main.Game1 %0, ptr %2, align 8
|
||||||
|
%3 = getelementptr inbounds %main.Game1, ptr %2, i32 0, i32 0
|
||||||
|
%4 = load ptr, ptr %3, align 8
|
||||||
|
call void @"github.com/goplus/llgo/cl/internal/foo.(*Game).initGame"(ptr %4)
|
||||||
|
ret void
|
||||||
|
}
|
||||||
|
|
||||||
|
define void @"main.(*Game1).Load"(ptr %0) {
|
||||||
|
_llgo_0:
|
||||||
|
%1 = getelementptr inbounds %main.Game1, ptr %0, i32 0, i32 0
|
||||||
|
%2 = load ptr, ptr %1, align 8
|
||||||
|
call void @"github.com/goplus/llgo/cl/internal/foo.(*Game).Load"(ptr %2)
|
||||||
|
ret void
|
||||||
|
}
|
||||||
|
|
||||||
|
define void @"main.(*Game1).initGame"(ptr %0) {
|
||||||
|
_llgo_0:
|
||||||
|
%1 = getelementptr inbounds %main.Game1, ptr %0, i32 0, i32 0
|
||||||
|
%2 = load ptr, ptr %1, align 8
|
||||||
|
call void @"github.com/goplus/llgo/cl/internal/foo.(*Game).initGame"(ptr %2)
|
||||||
|
ret void
|
||||||
|
}
|
||||||
|
|
||||||
|
define void @"main.(*Game2).initGame"(ptr %0) {
|
||||||
|
_llgo_0:
|
||||||
|
ret void
|
||||||
|
}
|
||||||
|
|
||||||
|
define void @main.init() {
|
||||||
|
_llgo_0:
|
||||||
|
%0 = load i1, ptr @"main.init$guard", align 1
|
||||||
|
br i1 %0, label %_llgo_2, label %_llgo_1
|
||||||
|
|
||||||
|
_llgo_1: ; preds = %_llgo_0
|
||||||
|
store i1 true, ptr @"main.init$guard", align 1
|
||||||
|
call void @"github.com/goplus/llgo/cl/internal/foo.init"()
|
||||||
|
call void @"main.init$after"()
|
||||||
|
br label %_llgo_2
|
||||||
|
|
||||||
|
_llgo_2: ; preds = %_llgo_1, %_llgo_0
|
||||||
|
ret void
|
||||||
|
}
|
||||||
|
|
||||||
|
define i32 @main(i32 %0, ptr %1) {
|
||||||
|
_llgo_0:
|
||||||
|
store i32 %0, ptr @__llgo_argc, align 4
|
||||||
|
store ptr %1, ptr @__llgo_argv, align 8
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
|
call void @main.init()
|
||||||
|
%2 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocZ"(i64 8)
|
||||||
|
%3 = getelementptr inbounds %main.Game1, ptr %2, i32 0, i32 0
|
||||||
|
%4 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocZ"(i64 0)
|
||||||
|
store ptr %4, ptr %3, align 8
|
||||||
|
%5 = load ptr, ptr @"*_llgo_main.Game1", align 8
|
||||||
|
%6 = alloca %"github.com/goplus/llgo/internal/runtime.eface", align 8
|
||||||
|
%7 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.eface", ptr %6, i32 0, i32 0
|
||||||
|
store ptr %5, ptr %7, align 8
|
||||||
|
%8 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.eface", ptr %6, i32 0, i32 1
|
||||||
|
store ptr %2, ptr %8, align 8
|
||||||
|
%9 = load %"github.com/goplus/llgo/internal/runtime.eface", ptr %6, align 8
|
||||||
|
%10 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocZ"(i64 0)
|
||||||
|
%11 = load ptr, ptr @"*_llgo_main.Game2", align 8
|
||||||
|
%12 = alloca %"github.com/goplus/llgo/internal/runtime.eface", align 8
|
||||||
|
%13 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.eface", ptr %12, i32 0, i32 0
|
||||||
|
store ptr %11, ptr %13, align 8
|
||||||
|
%14 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.eface", ptr %12, i32 0, i32 1
|
||||||
|
store ptr %10, ptr %14, align 8
|
||||||
|
%15 = load %"github.com/goplus/llgo/internal/runtime.eface", ptr %12, align 8
|
||||||
|
%16 = extractvalue %"github.com/goplus/llgo/internal/runtime.eface" %9, 0
|
||||||
|
%17 = load ptr, ptr @"_llgo_github.com/goplus/llgo/cl/internal/foo.Gamer", align 8
|
||||||
|
%18 = call i1 @"github.com/goplus/llgo/internal/runtime.Implements"(ptr %17, ptr %16)
|
||||||
|
br i1 %18, label %_llgo_3, label %_llgo_4
|
||||||
|
|
||||||
|
_llgo_1: ; preds = %_llgo_5
|
||||||
|
%19 = call ptr @"github.com/goplus/llgo/internal/runtime.IfacePtrData"(%"github.com/goplus/llgo/internal/runtime.iface" %48)
|
||||||
|
%20 = extractvalue %"github.com/goplus/llgo/internal/runtime.iface" %48, 0
|
||||||
|
%21 = getelementptr ptr, ptr %20, i64 3
|
||||||
|
%22 = load ptr, ptr %21, align 8
|
||||||
|
%23 = alloca { ptr, ptr }, align 8
|
||||||
|
%24 = getelementptr inbounds { ptr, ptr }, ptr %23, i32 0, i32 0
|
||||||
|
store ptr %22, ptr %24, align 8
|
||||||
|
%25 = getelementptr inbounds { ptr, ptr }, ptr %23, i32 0, i32 1
|
||||||
|
store ptr %19, ptr %25, align 8
|
||||||
|
%26 = load { ptr, ptr }, ptr %23, align 8
|
||||||
|
%27 = extractvalue { ptr, ptr } %26, 1
|
||||||
|
%28 = extractvalue { ptr, ptr } %26, 0
|
||||||
|
call void %28(ptr %27)
|
||||||
|
br label %_llgo_2
|
||||||
|
|
||||||
|
_llgo_2: ; preds = %_llgo_1, %_llgo_5
|
||||||
|
%29 = extractvalue %"github.com/goplus/llgo/internal/runtime.eface" %15, 0
|
||||||
|
%30 = load ptr, ptr @"_llgo_github.com/goplus/llgo/cl/internal/foo.Gamer", align 8
|
||||||
|
%31 = call i1 @"github.com/goplus/llgo/internal/runtime.Implements"(ptr %30, ptr %29)
|
||||||
|
br i1 %31, label %_llgo_6, label %_llgo_7
|
||||||
|
|
||||||
|
_llgo_3: ; preds = %_llgo_0
|
||||||
|
%32 = extractvalue %"github.com/goplus/llgo/internal/runtime.eface" %9, 1
|
||||||
|
%33 = load ptr, ptr @"main.iface$sO8a1LvuUsjXwiwaC6sR9-L4DiYgiOnZi7iosyShJXg", align 8
|
||||||
|
%34 = call ptr @"github.com/goplus/llgo/internal/runtime.NewItab"(ptr %33, ptr %16)
|
||||||
|
%35 = alloca %"github.com/goplus/llgo/internal/runtime.iface", align 8
|
||||||
|
%36 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.iface", ptr %35, i32 0, i32 0
|
||||||
|
store ptr %34, ptr %36, align 8
|
||||||
|
%37 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.iface", ptr %35, i32 0, i32 1
|
||||||
|
store ptr %32, ptr %37, align 8
|
||||||
|
%38 = load %"github.com/goplus/llgo/internal/runtime.iface", ptr %35, align 8
|
||||||
|
%39 = alloca { %"github.com/goplus/llgo/internal/runtime.iface", i1 }, align 8
|
||||||
|
%40 = getelementptr inbounds { %"github.com/goplus/llgo/internal/runtime.iface", i1 }, ptr %39, i32 0, i32 0
|
||||||
|
store %"github.com/goplus/llgo/internal/runtime.iface" %38, ptr %40, align 8
|
||||||
|
%41 = getelementptr inbounds { %"github.com/goplus/llgo/internal/runtime.iface", i1 }, ptr %39, i32 0, i32 1
|
||||||
|
store i1 true, ptr %41, align 1
|
||||||
|
%42 = load { %"github.com/goplus/llgo/internal/runtime.iface", i1 }, ptr %39, align 8
|
||||||
|
br label %_llgo_5
|
||||||
|
|
||||||
|
_llgo_4: ; preds = %_llgo_0
|
||||||
|
%43 = alloca { %"github.com/goplus/llgo/internal/runtime.iface", i1 }, align 8
|
||||||
|
%44 = getelementptr inbounds { %"github.com/goplus/llgo/internal/runtime.iface", i1 }, ptr %43, i32 0, i32 0
|
||||||
|
store { ptr, ptr } zeroinitializer, ptr %44, align 8
|
||||||
|
%45 = getelementptr inbounds { %"github.com/goplus/llgo/internal/runtime.iface", i1 }, ptr %43, i32 0, i32 1
|
||||||
|
store i1 false, ptr %45, align 1
|
||||||
|
%46 = load { %"github.com/goplus/llgo/internal/runtime.iface", i1 }, ptr %43, align 8
|
||||||
|
br label %_llgo_5
|
||||||
|
|
||||||
|
_llgo_5: ; preds = %_llgo_4, %_llgo_3
|
||||||
|
%47 = phi { %"github.com/goplus/llgo/internal/runtime.iface", i1 } [ %42, %_llgo_3 ], [ %46, %_llgo_4 ]
|
||||||
|
%48 = extractvalue { %"github.com/goplus/llgo/internal/runtime.iface", i1 } %47, 0
|
||||||
|
%49 = extractvalue { %"github.com/goplus/llgo/internal/runtime.iface", i1 } %47, 1
|
||||||
|
%50 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%51 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %50, i32 0, i32 0
|
||||||
|
store ptr @26, ptr %51, align 8
|
||||||
|
%52 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %50, i32 0, i32 1
|
||||||
|
store i64 2, ptr %52, align 4
|
||||||
|
%53 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %50, align 8
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintString"(%"github.com/goplus/llgo/internal/runtime.String" %53)
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintByte"(i8 32)
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintIface"(%"github.com/goplus/llgo/internal/runtime.iface" %48)
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintByte"(i8 32)
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintBool"(i1 %49)
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintByte"(i8 10)
|
||||||
|
br i1 %49, label %_llgo_1, label %_llgo_2
|
||||||
|
|
||||||
|
_llgo_6: ; preds = %_llgo_2
|
||||||
|
%54 = extractvalue %"github.com/goplus/llgo/internal/runtime.eface" %15, 1
|
||||||
|
%55 = load ptr, ptr @"main.iface$sO8a1LvuUsjXwiwaC6sR9-L4DiYgiOnZi7iosyShJXg", align 8
|
||||||
|
%56 = call ptr @"github.com/goplus/llgo/internal/runtime.NewItab"(ptr %55, ptr %29)
|
||||||
|
%57 = alloca %"github.com/goplus/llgo/internal/runtime.iface", align 8
|
||||||
|
%58 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.iface", ptr %57, i32 0, i32 0
|
||||||
|
store ptr %56, ptr %58, align 8
|
||||||
|
%59 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.iface", ptr %57, i32 0, i32 1
|
||||||
|
store ptr %54, ptr %59, align 8
|
||||||
|
%60 = load %"github.com/goplus/llgo/internal/runtime.iface", ptr %57, align 8
|
||||||
|
%61 = alloca { %"github.com/goplus/llgo/internal/runtime.iface", i1 }, align 8
|
||||||
|
%62 = getelementptr inbounds { %"github.com/goplus/llgo/internal/runtime.iface", i1 }, ptr %61, i32 0, i32 0
|
||||||
|
store %"github.com/goplus/llgo/internal/runtime.iface" %60, ptr %62, align 8
|
||||||
|
%63 = getelementptr inbounds { %"github.com/goplus/llgo/internal/runtime.iface", i1 }, ptr %61, i32 0, i32 1
|
||||||
|
store i1 true, ptr %63, align 1
|
||||||
|
%64 = load { %"github.com/goplus/llgo/internal/runtime.iface", i1 }, ptr %61, align 8
|
||||||
|
br label %_llgo_8
|
||||||
|
|
||||||
|
_llgo_7: ; preds = %_llgo_2
|
||||||
|
%65 = alloca { %"github.com/goplus/llgo/internal/runtime.iface", i1 }, align 8
|
||||||
|
%66 = getelementptr inbounds { %"github.com/goplus/llgo/internal/runtime.iface", i1 }, ptr %65, i32 0, i32 0
|
||||||
|
store { ptr, ptr } zeroinitializer, ptr %66, align 8
|
||||||
|
%67 = getelementptr inbounds { %"github.com/goplus/llgo/internal/runtime.iface", i1 }, ptr %65, i32 0, i32 1
|
||||||
|
store i1 false, ptr %67, align 1
|
||||||
|
%68 = load { %"github.com/goplus/llgo/internal/runtime.iface", i1 }, ptr %65, align 8
|
||||||
|
br label %_llgo_8
|
||||||
|
|
||||||
|
_llgo_8: ; preds = %_llgo_7, %_llgo_6
|
||||||
|
%69 = phi { %"github.com/goplus/llgo/internal/runtime.iface", i1 } [ %64, %_llgo_6 ], [ %68, %_llgo_7 ]
|
||||||
|
%70 = extractvalue { %"github.com/goplus/llgo/internal/runtime.iface", i1 } %69, 0
|
||||||
|
%71 = extractvalue { %"github.com/goplus/llgo/internal/runtime.iface", i1 } %69, 1
|
||||||
|
%72 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%73 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %72, i32 0, i32 0
|
||||||
|
store ptr @27, ptr %73, align 8
|
||||||
|
%74 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %72, i32 0, i32 1
|
||||||
|
store i64 4, ptr %74, align 4
|
||||||
|
%75 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %72, align 8
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintString"(%"github.com/goplus/llgo/internal/runtime.String" %75)
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintByte"(i8 32)
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintIface"(%"github.com/goplus/llgo/internal/runtime.iface" %70)
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintByte"(i8 32)
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintBool"(i1 %71)
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintByte"(i8 10)
|
||||||
|
ret i32 0
|
||||||
|
}
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.Zeroinit"(ptr, i64)
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/cl/internal/foo.(*Game).Load"(ptr)
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/cl/internal/foo.(*Game).initGame"(ptr)
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/cl/internal/foo.init"()
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.AllocZ"(i64)
|
||||||
|
|
||||||
|
define void @"main.init$after"() {
|
||||||
|
_llgo_0:
|
||||||
|
%0 = load ptr, ptr @_llgo_main.Game1, align 8
|
||||||
|
%1 = icmp eq ptr %0, null
|
||||||
|
br i1 %1, label %_llgo_1, label %_llgo_2
|
||||||
|
|
||||||
|
_llgo_1: ; preds = %_llgo_0
|
||||||
|
%2 = call ptr @"github.com/goplus/llgo/internal/runtime.NewNamed"(i64 25, i64 2, i64 2)
|
||||||
|
store ptr %2, ptr @_llgo_main.Game1, align 8
|
||||||
|
br label %_llgo_2
|
||||||
|
|
||||||
|
_llgo_2: ; preds = %_llgo_1, %_llgo_0
|
||||||
|
%3 = load ptr, ptr @"_llgo_github.com/goplus/llgo/cl/internal/foo.Game", align 8
|
||||||
|
%4 = icmp eq ptr %3, null
|
||||||
|
br i1 %4, label %_llgo_3, label %_llgo_4
|
||||||
|
|
||||||
|
_llgo_3: ; preds = %_llgo_2
|
||||||
|
%5 = call ptr @"github.com/goplus/llgo/internal/runtime.NewNamed"(i64 25, i64 0, i64 2)
|
||||||
|
store ptr %5, ptr @"_llgo_github.com/goplus/llgo/cl/internal/foo.Game", align 8
|
||||||
|
br label %_llgo_4
|
||||||
|
|
||||||
|
_llgo_4: ; preds = %_llgo_3, %_llgo_2
|
||||||
|
%6 = load ptr, ptr @"_llgo_struct$n1H8J_3prDN3firMwPxBLVTkE5hJ9Di-AqNvaC9jczw", align 8
|
||||||
|
%7 = icmp eq ptr %6, null
|
||||||
|
br i1 %7, label %_llgo_5, label %_llgo_6
|
||||||
|
|
||||||
|
_llgo_5: ; preds = %_llgo_4
|
||||||
|
%8 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%9 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %8, i32 0, i32 0
|
||||||
|
store ptr @0, ptr %9, align 8
|
||||||
|
%10 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %8, i32 0, i32 1
|
||||||
|
store i64 4, ptr %10, align 4
|
||||||
|
%11 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %8, align 8
|
||||||
|
%12 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocU"(i64 0)
|
||||||
|
%13 = alloca %"github.com/goplus/llgo/internal/runtime.Slice", align 8
|
||||||
|
%14 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %13, i32 0, i32 0
|
||||||
|
store ptr %12, ptr %14, align 8
|
||||||
|
%15 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %13, i32 0, i32 1
|
||||||
|
store i64 0, ptr %15, align 4
|
||||||
|
%16 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %13, i32 0, i32 2
|
||||||
|
store i64 0, ptr %16, align 4
|
||||||
|
%17 = load %"github.com/goplus/llgo/internal/runtime.Slice", ptr %13, align 8
|
||||||
|
%18 = call ptr @"github.com/goplus/llgo/internal/runtime.Struct"(%"github.com/goplus/llgo/internal/runtime.String" %11, i64 0, %"github.com/goplus/llgo/internal/runtime.Slice" %17)
|
||||||
|
store ptr %18, ptr @"_llgo_struct$n1H8J_3prDN3firMwPxBLVTkE5hJ9Di-AqNvaC9jczw", align 8
|
||||||
|
br label %_llgo_6
|
||||||
|
|
||||||
|
_llgo_6: ; preds = %_llgo_5, %_llgo_4
|
||||||
|
%19 = load ptr, ptr @"_llgo_struct$n1H8J_3prDN3firMwPxBLVTkE5hJ9Di-AqNvaC9jczw", align 8
|
||||||
|
br i1 %4, label %_llgo_7, label %_llgo_8
|
||||||
|
|
||||||
|
_llgo_7: ; preds = %_llgo_6
|
||||||
|
%20 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%21 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %20, i32 0, i32 0
|
||||||
|
store ptr @1, ptr %21, align 8
|
||||||
|
%22 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %20, i32 0, i32 1
|
||||||
|
store i64 4, ptr %22, align 4
|
||||||
|
%23 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %20, align 8
|
||||||
|
%24 = load ptr, ptr @"_llgo_func$2_iS07vIlF2_rZqWB5eU0IvP_9HviM4MYZNkXZDvbac", align 8
|
||||||
|
%25 = icmp eq ptr %24, null
|
||||||
|
br i1 %25, label %_llgo_9, label %_llgo_10
|
||||||
|
|
||||||
|
_llgo_8: ; preds = %_llgo_10, %_llgo_6
|
||||||
|
%26 = load ptr, ptr @"_llgo_github.com/goplus/llgo/cl/internal/foo.Game", align 8
|
||||||
|
%27 = load ptr, ptr @"*_llgo_github.com/goplus/llgo/cl/internal/foo.Game", align 8
|
||||||
|
%28 = icmp eq ptr %27, null
|
||||||
|
br i1 %28, label %_llgo_11, label %_llgo_12
|
||||||
|
|
||||||
|
_llgo_9: ; preds = %_llgo_7
|
||||||
|
%29 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocU"(i64 0)
|
||||||
|
%30 = alloca %"github.com/goplus/llgo/internal/runtime.Slice", align 8
|
||||||
|
%31 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %30, i32 0, i32 0
|
||||||
|
store ptr %29, ptr %31, align 8
|
||||||
|
%32 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %30, i32 0, i32 1
|
||||||
|
store i64 0, ptr %32, align 4
|
||||||
|
%33 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %30, i32 0, i32 2
|
||||||
|
store i64 0, ptr %33, align 4
|
||||||
|
%34 = load %"github.com/goplus/llgo/internal/runtime.Slice", ptr %30, align 8
|
||||||
|
%35 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocU"(i64 0)
|
||||||
|
%36 = alloca %"github.com/goplus/llgo/internal/runtime.Slice", align 8
|
||||||
|
%37 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %36, i32 0, i32 0
|
||||||
|
store ptr %35, ptr %37, align 8
|
||||||
|
%38 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %36, i32 0, i32 1
|
||||||
|
store i64 0, ptr %38, align 4
|
||||||
|
%39 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %36, i32 0, i32 2
|
||||||
|
store i64 0, ptr %39, align 4
|
||||||
|
%40 = load %"github.com/goplus/llgo/internal/runtime.Slice", ptr %36, align 8
|
||||||
|
%41 = call ptr @"github.com/goplus/llgo/internal/runtime.Func"(%"github.com/goplus/llgo/internal/runtime.Slice" %34, %"github.com/goplus/llgo/internal/runtime.Slice" %40, i1 false)
|
||||||
|
store ptr %41, ptr @"_llgo_func$2_iS07vIlF2_rZqWB5eU0IvP_9HviM4MYZNkXZDvbac", align 8
|
||||||
|
br label %_llgo_10
|
||||||
|
|
||||||
|
_llgo_10: ; preds = %_llgo_9, %_llgo_7
|
||||||
|
%42 = load ptr, ptr @"_llgo_func$2_iS07vIlF2_rZqWB5eU0IvP_9HviM4MYZNkXZDvbac", align 8
|
||||||
|
%43 = alloca %"github.com/goplus/llgo/internal/abi.Method", align 8
|
||||||
|
%44 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %43, i32 0, i32 0
|
||||||
|
store %"github.com/goplus/llgo/internal/runtime.String" %23, ptr %44, align 8
|
||||||
|
%45 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %43, i32 0, i32 1
|
||||||
|
store ptr %42, ptr %45, align 8
|
||||||
|
%46 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %43, i32 0, i32 2
|
||||||
|
store ptr @"github.com/goplus/llgo/cl/internal/foo.(*Game).Load", ptr %46, align 8
|
||||||
|
%47 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %43, i32 0, i32 3
|
||||||
|
store ptr @"github.com/goplus/llgo/cl/internal/foo.(*Game).Load", ptr %47, align 8
|
||||||
|
%48 = load %"github.com/goplus/llgo/internal/abi.Method", ptr %43, align 8
|
||||||
|
%49 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%50 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %49, i32 0, i32 0
|
||||||
|
store ptr @2, ptr %50, align 8
|
||||||
|
%51 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %49, i32 0, i32 1
|
||||||
|
store i64 8, ptr %51, align 4
|
||||||
|
%52 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %49, align 8
|
||||||
|
%53 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%54 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %53, i32 0, i32 0
|
||||||
|
store ptr @3, ptr %54, align 8
|
||||||
|
%55 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %53, i32 0, i32 1
|
||||||
|
store i64 47, ptr %55, align 4
|
||||||
|
%56 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %53, align 8
|
||||||
|
%57 = load ptr, ptr @"_llgo_func$2_iS07vIlF2_rZqWB5eU0IvP_9HviM4MYZNkXZDvbac", align 8
|
||||||
|
%58 = alloca %"github.com/goplus/llgo/internal/abi.Method", align 8
|
||||||
|
%59 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %58, i32 0, i32 0
|
||||||
|
store %"github.com/goplus/llgo/internal/runtime.String" %56, ptr %59, align 8
|
||||||
|
%60 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %58, i32 0, i32 1
|
||||||
|
store ptr %57, ptr %60, align 8
|
||||||
|
%61 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %58, i32 0, i32 2
|
||||||
|
store ptr @"github.com/goplus/llgo/cl/internal/foo.(*Game).initGame", ptr %61, align 8
|
||||||
|
%62 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %58, i32 0, i32 3
|
||||||
|
store ptr @"github.com/goplus/llgo/cl/internal/foo.(*Game).initGame", ptr %62, align 8
|
||||||
|
%63 = load %"github.com/goplus/llgo/internal/abi.Method", ptr %58, align 8
|
||||||
|
%64 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocU"(i64 80)
|
||||||
|
%65 = getelementptr %"github.com/goplus/llgo/internal/abi.Method", ptr %64, i64 0
|
||||||
|
store %"github.com/goplus/llgo/internal/abi.Method" %48, ptr %65, align 8
|
||||||
|
%66 = getelementptr %"github.com/goplus/llgo/internal/abi.Method", ptr %64, i64 1
|
||||||
|
store %"github.com/goplus/llgo/internal/abi.Method" %63, ptr %66, align 8
|
||||||
|
%67 = alloca %"github.com/goplus/llgo/internal/runtime.Slice", align 8
|
||||||
|
%68 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %67, i32 0, i32 0
|
||||||
|
store ptr %64, ptr %68, align 8
|
||||||
|
%69 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %67, i32 0, i32 1
|
||||||
|
store i64 2, ptr %69, align 4
|
||||||
|
%70 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %67, i32 0, i32 2
|
||||||
|
store i64 2, ptr %70, align 4
|
||||||
|
%71 = load %"github.com/goplus/llgo/internal/runtime.Slice", ptr %67, align 8
|
||||||
|
%72 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%73 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %72, i32 0, i32 0
|
||||||
|
store ptr @4, ptr %73, align 8
|
||||||
|
%74 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %72, i32 0, i32 1
|
||||||
|
store i64 38, ptr %74, align 4
|
||||||
|
%75 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %72, align 8
|
||||||
|
%76 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%77 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %76, i32 0, i32 0
|
||||||
|
store ptr @5, ptr %77, align 8
|
||||||
|
%78 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %76, i32 0, i32 1
|
||||||
|
store i64 43, ptr %78, align 4
|
||||||
|
%79 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %76, align 8
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.InitNamed"(ptr %5, %"github.com/goplus/llgo/internal/runtime.String" %75, %"github.com/goplus/llgo/internal/runtime.String" %79, ptr %19, { ptr, i64, i64 } zeroinitializer, %"github.com/goplus/llgo/internal/runtime.Slice" %71)
|
||||||
|
br label %_llgo_8
|
||||||
|
|
||||||
|
_llgo_11: ; preds = %_llgo_8
|
||||||
|
%80 = call ptr @"github.com/goplus/llgo/internal/runtime.PointerTo"(ptr %26)
|
||||||
|
store ptr %80, ptr @"*_llgo_github.com/goplus/llgo/cl/internal/foo.Game", align 8
|
||||||
|
br label %_llgo_12
|
||||||
|
|
||||||
|
_llgo_12: ; preds = %_llgo_11, %_llgo_8
|
||||||
|
%81 = load ptr, ptr @"*_llgo_github.com/goplus/llgo/cl/internal/foo.Game", align 8
|
||||||
|
%82 = load ptr, ptr @"_llgo_struct$cJmCzeVn0orHWafCrTGAnbbAF46F2A4Fms4bJBm8ITI", align 8
|
||||||
|
%83 = icmp eq ptr %82, null
|
||||||
|
br i1 %83, label %_llgo_13, label %_llgo_14
|
||||||
|
|
||||||
|
_llgo_13: ; preds = %_llgo_12
|
||||||
|
%84 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%85 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %84, i32 0, i32 0
|
||||||
|
store ptr @6, ptr %85, align 8
|
||||||
|
%86 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %84, i32 0, i32 1
|
||||||
|
store i64 4, ptr %86, align 4
|
||||||
|
%87 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %84, align 8
|
||||||
|
%88 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%89 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %88, i32 0, i32 0
|
||||||
|
store ptr @7, ptr %89, align 8
|
||||||
|
%90 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %88, i32 0, i32 1
|
||||||
|
store i64 0, ptr %90, align 4
|
||||||
|
%91 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %88, align 8
|
||||||
|
%92 = call %"github.com/goplus/llgo/internal/abi.StructField" @"github.com/goplus/llgo/internal/runtime.StructField"(%"github.com/goplus/llgo/internal/runtime.String" %87, ptr %81, i64 0, %"github.com/goplus/llgo/internal/runtime.String" %91, i1 true)
|
||||||
|
%93 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%94 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %93, i32 0, i32 0
|
||||||
|
store ptr @8, ptr %94, align 8
|
||||||
|
%95 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %93, i32 0, i32 1
|
||||||
|
store i64 4, ptr %95, align 4
|
||||||
|
%96 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %93, align 8
|
||||||
|
%97 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocU"(i64 56)
|
||||||
|
%98 = getelementptr %"github.com/goplus/llgo/internal/abi.StructField", ptr %97, i64 0
|
||||||
|
store %"github.com/goplus/llgo/internal/abi.StructField" %92, ptr %98, align 8
|
||||||
|
%99 = alloca %"github.com/goplus/llgo/internal/runtime.Slice", align 8
|
||||||
|
%100 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %99, i32 0, i32 0
|
||||||
|
store ptr %97, ptr %100, align 8
|
||||||
|
%101 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %99, i32 0, i32 1
|
||||||
|
store i64 1, ptr %101, align 4
|
||||||
|
%102 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %99, i32 0, i32 2
|
||||||
|
store i64 1, ptr %102, align 4
|
||||||
|
%103 = load %"github.com/goplus/llgo/internal/runtime.Slice", ptr %99, align 8
|
||||||
|
%104 = call ptr @"github.com/goplus/llgo/internal/runtime.Struct"(%"github.com/goplus/llgo/internal/runtime.String" %96, i64 8, %"github.com/goplus/llgo/internal/runtime.Slice" %103)
|
||||||
|
store ptr %104, ptr @"_llgo_struct$cJmCzeVn0orHWafCrTGAnbbAF46F2A4Fms4bJBm8ITI", align 8
|
||||||
|
br label %_llgo_14
|
||||||
|
|
||||||
|
_llgo_14: ; preds = %_llgo_13, %_llgo_12
|
||||||
|
%105 = load ptr, ptr @"_llgo_struct$cJmCzeVn0orHWafCrTGAnbbAF46F2A4Fms4bJBm8ITI", align 8
|
||||||
|
br i1 %1, label %_llgo_15, label %_llgo_16
|
||||||
|
|
||||||
|
_llgo_15: ; preds = %_llgo_14
|
||||||
|
%106 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%107 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %106, i32 0, i32 0
|
||||||
|
store ptr @9, ptr %107, align 8
|
||||||
|
%108 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %106, i32 0, i32 1
|
||||||
|
store i64 4, ptr %108, align 4
|
||||||
|
%109 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %106, align 8
|
||||||
|
%110 = load ptr, ptr @"_llgo_func$2_iS07vIlF2_rZqWB5eU0IvP_9HviM4MYZNkXZDvbac", align 8
|
||||||
|
%111 = alloca %"github.com/goplus/llgo/internal/abi.Method", align 8
|
||||||
|
%112 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %111, i32 0, i32 0
|
||||||
|
store %"github.com/goplus/llgo/internal/runtime.String" %109, ptr %112, align 8
|
||||||
|
%113 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %111, i32 0, i32 1
|
||||||
|
store ptr %110, ptr %113, align 8
|
||||||
|
%114 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %111, i32 0, i32 2
|
||||||
|
store ptr @"github.com/goplus/llgo/cl/internal/foo.(*Game).Load", ptr %114, align 8
|
||||||
|
%115 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %111, i32 0, i32 3
|
||||||
|
store ptr @"github.com/goplus/llgo/cl/internal/foo.(*Game).Load", ptr %115, align 8
|
||||||
|
%116 = load %"github.com/goplus/llgo/internal/abi.Method", ptr %111, align 8
|
||||||
|
%117 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%118 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %117, i32 0, i32 0
|
||||||
|
store ptr @10, ptr %118, align 8
|
||||||
|
%119 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %117, i32 0, i32 1
|
||||||
|
store i64 8, ptr %119, align 4
|
||||||
|
%120 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %117, align 8
|
||||||
|
%121 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%122 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %121, i32 0, i32 0
|
||||||
|
store ptr @11, ptr %122, align 8
|
||||||
|
%123 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %121, i32 0, i32 1
|
||||||
|
store i64 47, ptr %123, align 4
|
||||||
|
%124 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %121, align 8
|
||||||
|
%125 = load ptr, ptr @"_llgo_func$2_iS07vIlF2_rZqWB5eU0IvP_9HviM4MYZNkXZDvbac", align 8
|
||||||
|
%126 = alloca %"github.com/goplus/llgo/internal/abi.Method", align 8
|
||||||
|
%127 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %126, i32 0, i32 0
|
||||||
|
store %"github.com/goplus/llgo/internal/runtime.String" %124, ptr %127, align 8
|
||||||
|
%128 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %126, i32 0, i32 1
|
||||||
|
store ptr %125, ptr %128, align 8
|
||||||
|
%129 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %126, i32 0, i32 2
|
||||||
|
store ptr @"github.com/goplus/llgo/cl/internal/foo.(*Game).initGame", ptr %129, align 8
|
||||||
|
%130 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %126, i32 0, i32 3
|
||||||
|
store ptr @"github.com/goplus/llgo/cl/internal/foo.(*Game).initGame", ptr %130, align 8
|
||||||
|
%131 = load %"github.com/goplus/llgo/internal/abi.Method", ptr %126, align 8
|
||||||
|
%132 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocU"(i64 80)
|
||||||
|
%133 = getelementptr %"github.com/goplus/llgo/internal/abi.Method", ptr %132, i64 0
|
||||||
|
store %"github.com/goplus/llgo/internal/abi.Method" %116, ptr %133, align 8
|
||||||
|
%134 = getelementptr %"github.com/goplus/llgo/internal/abi.Method", ptr %132, i64 1
|
||||||
|
store %"github.com/goplus/llgo/internal/abi.Method" %131, ptr %134, align 8
|
||||||
|
%135 = alloca %"github.com/goplus/llgo/internal/runtime.Slice", align 8
|
||||||
|
%136 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %135, i32 0, i32 0
|
||||||
|
store ptr %132, ptr %136, align 8
|
||||||
|
%137 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %135, i32 0, i32 1
|
||||||
|
store i64 2, ptr %137, align 4
|
||||||
|
%138 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %135, i32 0, i32 2
|
||||||
|
store i64 2, ptr %138, align 4
|
||||||
|
%139 = load %"github.com/goplus/llgo/internal/runtime.Slice", ptr %135, align 8
|
||||||
|
%140 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%141 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %140, i32 0, i32 0
|
||||||
|
store ptr @12, ptr %141, align 8
|
||||||
|
%142 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %140, i32 0, i32 1
|
||||||
|
store i64 4, ptr %142, align 4
|
||||||
|
%143 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %140, align 8
|
||||||
|
%144 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%145 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %144, i32 0, i32 0
|
||||||
|
store ptr @13, ptr %145, align 8
|
||||||
|
%146 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %144, i32 0, i32 1
|
||||||
|
store i64 10, ptr %146, align 4
|
||||||
|
%147 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %144, align 8
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.InitNamed"(ptr %2, %"github.com/goplus/llgo/internal/runtime.String" %143, %"github.com/goplus/llgo/internal/runtime.String" %147, ptr %105, { ptr, i64, i64 } zeroinitializer, %"github.com/goplus/llgo/internal/runtime.Slice" %139)
|
||||||
|
br label %_llgo_16
|
||||||
|
|
||||||
|
_llgo_16: ; preds = %_llgo_15, %_llgo_14
|
||||||
|
%148 = load ptr, ptr @_llgo_main.Game1, align 8
|
||||||
|
%149 = load ptr, ptr @"*_llgo_main.Game1", align 8
|
||||||
|
%150 = icmp eq ptr %149, null
|
||||||
|
br i1 %150, label %_llgo_17, label %_llgo_18
|
||||||
|
|
||||||
|
_llgo_17: ; preds = %_llgo_16
|
||||||
|
%151 = call ptr @"github.com/goplus/llgo/internal/runtime.PointerTo"(ptr %148)
|
||||||
|
store ptr %151, ptr @"*_llgo_main.Game1", align 8
|
||||||
|
br label %_llgo_18
|
||||||
|
|
||||||
|
_llgo_18: ; preds = %_llgo_17, %_llgo_16
|
||||||
|
%152 = load ptr, ptr @_llgo_main.Game2, align 8
|
||||||
|
%153 = icmp eq ptr %152, null
|
||||||
|
br i1 %153, label %_llgo_19, label %_llgo_20
|
||||||
|
|
||||||
|
_llgo_19: ; preds = %_llgo_18
|
||||||
|
%154 = call ptr @"github.com/goplus/llgo/internal/runtime.NewNamed"(i64 25, i64 0, i64 1)
|
||||||
|
store ptr %154, ptr @_llgo_main.Game2, align 8
|
||||||
|
br label %_llgo_20
|
||||||
|
|
||||||
|
_llgo_20: ; preds = %_llgo_19, %_llgo_18
|
||||||
|
%155 = load ptr, ptr @"_llgo_struct$n1H8J_3prDN3firMwPxBLVTkE5hJ9Di-AqNvaC9jczw", align 8
|
||||||
|
br i1 %153, label %_llgo_21, label %_llgo_22
|
||||||
|
|
||||||
|
_llgo_21: ; preds = %_llgo_20
|
||||||
|
%156 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%157 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %156, i32 0, i32 0
|
||||||
|
store ptr @14, ptr %157, align 8
|
||||||
|
%158 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %156, i32 0, i32 1
|
||||||
|
store i64 8, ptr %158, align 4
|
||||||
|
%159 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %156, align 8
|
||||||
|
%160 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%161 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %160, i32 0, i32 0
|
||||||
|
store ptr @15, ptr %161, align 8
|
||||||
|
%162 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %160, i32 0, i32 1
|
||||||
|
store i64 13, ptr %162, align 4
|
||||||
|
%163 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %160, align 8
|
||||||
|
%164 = load ptr, ptr @"_llgo_func$2_iS07vIlF2_rZqWB5eU0IvP_9HviM4MYZNkXZDvbac", align 8
|
||||||
|
%165 = alloca %"github.com/goplus/llgo/internal/abi.Method", align 8
|
||||||
|
%166 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %165, i32 0, i32 0
|
||||||
|
store %"github.com/goplus/llgo/internal/runtime.String" %163, ptr %166, align 8
|
||||||
|
%167 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %165, i32 0, i32 1
|
||||||
|
store ptr %164, ptr %167, align 8
|
||||||
|
%168 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %165, i32 0, i32 2
|
||||||
|
store ptr @"main.(*Game2).initGame", ptr %168, align 8
|
||||||
|
%169 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Method", ptr %165, i32 0, i32 3
|
||||||
|
store ptr @"main.(*Game2).initGame", ptr %169, align 8
|
||||||
|
%170 = load %"github.com/goplus/llgo/internal/abi.Method", ptr %165, align 8
|
||||||
|
%171 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocU"(i64 40)
|
||||||
|
%172 = getelementptr %"github.com/goplus/llgo/internal/abi.Method", ptr %171, i64 0
|
||||||
|
store %"github.com/goplus/llgo/internal/abi.Method" %170, ptr %172, align 8
|
||||||
|
%173 = alloca %"github.com/goplus/llgo/internal/runtime.Slice", align 8
|
||||||
|
%174 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %173, i32 0, i32 0
|
||||||
|
store ptr %171, ptr %174, align 8
|
||||||
|
%175 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %173, i32 0, i32 1
|
||||||
|
store i64 1, ptr %175, align 4
|
||||||
|
%176 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %173, i32 0, i32 2
|
||||||
|
store i64 1, ptr %176, align 4
|
||||||
|
%177 = load %"github.com/goplus/llgo/internal/runtime.Slice", ptr %173, align 8
|
||||||
|
%178 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%179 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %178, i32 0, i32 0
|
||||||
|
store ptr @16, ptr %179, align 8
|
||||||
|
%180 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %178, i32 0, i32 1
|
||||||
|
store i64 4, ptr %180, align 4
|
||||||
|
%181 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %178, align 8
|
||||||
|
%182 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%183 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %182, i32 0, i32 0
|
||||||
|
store ptr @17, ptr %183, align 8
|
||||||
|
%184 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %182, i32 0, i32 1
|
||||||
|
store i64 10, ptr %184, align 4
|
||||||
|
%185 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %182, align 8
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.InitNamed"(ptr %154, %"github.com/goplus/llgo/internal/runtime.String" %181, %"github.com/goplus/llgo/internal/runtime.String" %185, ptr %155, { ptr, i64, i64 } zeroinitializer, %"github.com/goplus/llgo/internal/runtime.Slice" %177)
|
||||||
|
br label %_llgo_22
|
||||||
|
|
||||||
|
_llgo_22: ; preds = %_llgo_21, %_llgo_20
|
||||||
|
%186 = load ptr, ptr @_llgo_main.Game2, align 8
|
||||||
|
%187 = load ptr, ptr @"*_llgo_main.Game2", align 8
|
||||||
|
%188 = icmp eq ptr %187, null
|
||||||
|
br i1 %188, label %_llgo_23, label %_llgo_24
|
||||||
|
|
||||||
|
_llgo_23: ; preds = %_llgo_22
|
||||||
|
%189 = call ptr @"github.com/goplus/llgo/internal/runtime.PointerTo"(ptr %186)
|
||||||
|
store ptr %189, ptr @"*_llgo_main.Game2", align 8
|
||||||
|
br label %_llgo_24
|
||||||
|
|
||||||
|
_llgo_24: ; preds = %_llgo_23, %_llgo_22
|
||||||
|
%190 = load ptr, ptr @"_llgo_func$2_iS07vIlF2_rZqWB5eU0IvP_9HviM4MYZNkXZDvbac", align 8
|
||||||
|
%191 = load ptr, ptr @"_llgo_func$2_iS07vIlF2_rZqWB5eU0IvP_9HviM4MYZNkXZDvbac", align 8
|
||||||
|
%192 = load ptr, ptr @"_llgo_github.com/goplus/llgo/cl/internal/foo.Gamer", align 8
|
||||||
|
%193 = icmp eq ptr %192, null
|
||||||
|
br i1 %193, label %_llgo_25, label %_llgo_26
|
||||||
|
|
||||||
|
_llgo_25: ; preds = %_llgo_24
|
||||||
|
%194 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%195 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %194, i32 0, i32 0
|
||||||
|
store ptr @18, ptr %195, align 8
|
||||||
|
%196 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %194, i32 0, i32 1
|
||||||
|
store i64 4, ptr %196, align 4
|
||||||
|
%197 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %194, align 8
|
||||||
|
%198 = alloca %"github.com/goplus/llgo/internal/abi.Imethod", align 8
|
||||||
|
%199 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Imethod", ptr %198, i32 0, i32 0
|
||||||
|
store %"github.com/goplus/llgo/internal/runtime.String" %197, ptr %199, align 8
|
||||||
|
%200 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Imethod", ptr %198, i32 0, i32 1
|
||||||
|
store ptr %190, ptr %200, align 8
|
||||||
|
%201 = load %"github.com/goplus/llgo/internal/abi.Imethod", ptr %198, align 8
|
||||||
|
%202 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%203 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %202, i32 0, i32 0
|
||||||
|
store ptr @19, ptr %203, align 8
|
||||||
|
%204 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %202, i32 0, i32 1
|
||||||
|
store i64 47, ptr %204, align 4
|
||||||
|
%205 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %202, align 8
|
||||||
|
%206 = alloca %"github.com/goplus/llgo/internal/abi.Imethod", align 8
|
||||||
|
%207 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Imethod", ptr %206, i32 0, i32 0
|
||||||
|
store %"github.com/goplus/llgo/internal/runtime.String" %205, ptr %207, align 8
|
||||||
|
%208 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Imethod", ptr %206, i32 0, i32 1
|
||||||
|
store ptr %191, ptr %208, align 8
|
||||||
|
%209 = load %"github.com/goplus/llgo/internal/abi.Imethod", ptr %206, align 8
|
||||||
|
%210 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocU"(i64 48)
|
||||||
|
%211 = getelementptr %"github.com/goplus/llgo/internal/abi.Imethod", ptr %210, i64 0
|
||||||
|
store %"github.com/goplus/llgo/internal/abi.Imethod" %201, ptr %211, align 8
|
||||||
|
%212 = getelementptr %"github.com/goplus/llgo/internal/abi.Imethod", ptr %210, i64 1
|
||||||
|
store %"github.com/goplus/llgo/internal/abi.Imethod" %209, ptr %212, align 8
|
||||||
|
%213 = alloca %"github.com/goplus/llgo/internal/runtime.Slice", align 8
|
||||||
|
%214 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %213, i32 0, i32 0
|
||||||
|
store ptr %210, ptr %214, align 8
|
||||||
|
%215 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %213, i32 0, i32 1
|
||||||
|
store i64 2, ptr %215, align 4
|
||||||
|
%216 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %213, i32 0, i32 2
|
||||||
|
store i64 2, ptr %216, align 4
|
||||||
|
%217 = load %"github.com/goplus/llgo/internal/runtime.Slice", ptr %213, align 8
|
||||||
|
%218 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%219 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %218, i32 0, i32 0
|
||||||
|
store ptr @20, ptr %219, align 8
|
||||||
|
%220 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %218, i32 0, i32 1
|
||||||
|
store i64 38, ptr %220, align 4
|
||||||
|
%221 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %218, align 8
|
||||||
|
%222 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%223 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %222, i32 0, i32 0
|
||||||
|
store ptr @21, ptr %223, align 8
|
||||||
|
%224 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %222, i32 0, i32 1
|
||||||
|
store i64 44, ptr %224, align 4
|
||||||
|
%225 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %222, align 8
|
||||||
|
%226 = call ptr @"github.com/goplus/llgo/internal/runtime.Interface"(%"github.com/goplus/llgo/internal/runtime.String" %221, %"github.com/goplus/llgo/internal/runtime.String" %225, %"github.com/goplus/llgo/internal/runtime.Slice" %217)
|
||||||
|
store ptr %226, ptr @"_llgo_github.com/goplus/llgo/cl/internal/foo.Gamer", align 8
|
||||||
|
br label %_llgo_26
|
||||||
|
|
||||||
|
_llgo_26: ; preds = %_llgo_25, %_llgo_24
|
||||||
|
%227 = load ptr, ptr @"_llgo_func$2_iS07vIlF2_rZqWB5eU0IvP_9HviM4MYZNkXZDvbac", align 8
|
||||||
|
%228 = load ptr, ptr @"_llgo_func$2_iS07vIlF2_rZqWB5eU0IvP_9HviM4MYZNkXZDvbac", align 8
|
||||||
|
%229 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%230 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %229, i32 0, i32 0
|
||||||
|
store ptr @22, ptr %230, align 8
|
||||||
|
%231 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %229, i32 0, i32 1
|
||||||
|
store i64 4, ptr %231, align 4
|
||||||
|
%232 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %229, align 8
|
||||||
|
%233 = alloca %"github.com/goplus/llgo/internal/abi.Imethod", align 8
|
||||||
|
%234 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Imethod", ptr %233, i32 0, i32 0
|
||||||
|
store %"github.com/goplus/llgo/internal/runtime.String" %232, ptr %234, align 8
|
||||||
|
%235 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Imethod", ptr %233, i32 0, i32 1
|
||||||
|
store ptr %227, ptr %235, align 8
|
||||||
|
%236 = load %"github.com/goplus/llgo/internal/abi.Imethod", ptr %233, align 8
|
||||||
|
%237 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%238 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %237, i32 0, i32 0
|
||||||
|
store ptr @23, ptr %238, align 8
|
||||||
|
%239 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %237, i32 0, i32 1
|
||||||
|
store i64 47, ptr %239, align 4
|
||||||
|
%240 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %237, align 8
|
||||||
|
%241 = alloca %"github.com/goplus/llgo/internal/abi.Imethod", align 8
|
||||||
|
%242 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Imethod", ptr %241, i32 0, i32 0
|
||||||
|
store %"github.com/goplus/llgo/internal/runtime.String" %240, ptr %242, align 8
|
||||||
|
%243 = getelementptr inbounds %"github.com/goplus/llgo/internal/abi.Imethod", ptr %241, i32 0, i32 1
|
||||||
|
store ptr %228, ptr %243, align 8
|
||||||
|
%244 = load %"github.com/goplus/llgo/internal/abi.Imethod", ptr %241, align 8
|
||||||
|
%245 = call ptr @"github.com/goplus/llgo/internal/runtime.AllocU"(i64 48)
|
||||||
|
%246 = getelementptr %"github.com/goplus/llgo/internal/abi.Imethod", ptr %245, i64 0
|
||||||
|
store %"github.com/goplus/llgo/internal/abi.Imethod" %236, ptr %246, align 8
|
||||||
|
%247 = getelementptr %"github.com/goplus/llgo/internal/abi.Imethod", ptr %245, i64 1
|
||||||
|
store %"github.com/goplus/llgo/internal/abi.Imethod" %244, ptr %247, align 8
|
||||||
|
%248 = alloca %"github.com/goplus/llgo/internal/runtime.Slice", align 8
|
||||||
|
%249 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %248, i32 0, i32 0
|
||||||
|
store ptr %245, ptr %249, align 8
|
||||||
|
%250 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %248, i32 0, i32 1
|
||||||
|
store i64 2, ptr %250, align 4
|
||||||
|
%251 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.Slice", ptr %248, i32 0, i32 2
|
||||||
|
store i64 2, ptr %251, align 4
|
||||||
|
%252 = load %"github.com/goplus/llgo/internal/runtime.Slice", ptr %248, align 8
|
||||||
|
%253 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%254 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %253, i32 0, i32 0
|
||||||
|
store ptr @24, ptr %254, align 8
|
||||||
|
%255 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %253, i32 0, i32 1
|
||||||
|
store i64 4, ptr %255, align 4
|
||||||
|
%256 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %253, align 8
|
||||||
|
%257 = alloca %"github.com/goplus/llgo/internal/runtime.String", align 8
|
||||||
|
%258 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %257, i32 0, i32 0
|
||||||
|
store ptr @25, ptr %258, align 8
|
||||||
|
%259 = getelementptr inbounds %"github.com/goplus/llgo/internal/runtime.String", ptr %257, i32 0, i32 1
|
||||||
|
store i64 0, ptr %259, align 4
|
||||||
|
%260 = load %"github.com/goplus/llgo/internal/runtime.String", ptr %257, align 8
|
||||||
|
%261 = call ptr @"github.com/goplus/llgo/internal/runtime.Interface"(%"github.com/goplus/llgo/internal/runtime.String" %256, %"github.com/goplus/llgo/internal/runtime.String" %260, %"github.com/goplus/llgo/internal/runtime.Slice" %252)
|
||||||
|
store ptr %261, ptr @"main.iface$sO8a1LvuUsjXwiwaC6sR9-L4DiYgiOnZi7iosyShJXg", align 8
|
||||||
|
ret void
|
||||||
|
}
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.NewNamed"(i64, i64, i64)
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.Struct"(%"github.com/goplus/llgo/internal/runtime.String", i64, %"github.com/goplus/llgo/internal/runtime.Slice")
|
||||||
|
|
||||||
|
declare %"github.com/goplus/llgo/internal/abi.StructField" @"github.com/goplus/llgo/internal/runtime.StructField"(%"github.com/goplus/llgo/internal/runtime.String", ptr, i64, %"github.com/goplus/llgo/internal/runtime.String", i1)
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.AllocU"(i64)
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.InitNamed"(ptr, %"github.com/goplus/llgo/internal/runtime.String", %"github.com/goplus/llgo/internal/runtime.String", ptr, %"github.com/goplus/llgo/internal/runtime.Slice", %"github.com/goplus/llgo/internal/runtime.Slice")
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.Func"(%"github.com/goplus/llgo/internal/runtime.Slice", %"github.com/goplus/llgo/internal/runtime.Slice", i1)
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.PointerTo"(ptr)
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.Interface"(%"github.com/goplus/llgo/internal/runtime.String", %"github.com/goplus/llgo/internal/runtime.String", %"github.com/goplus/llgo/internal/runtime.Slice")
|
||||||
|
|
||||||
|
declare i1 @"github.com/goplus/llgo/internal/runtime.Implements"(ptr, ptr)
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.NewItab"(ptr, ptr)
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.PrintString"(%"github.com/goplus/llgo/internal/runtime.String")
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.PrintByte"(i8)
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.PrintIface"(%"github.com/goplus/llgo/internal/runtime.iface")
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.PrintBool"(i1)
|
||||||
|
|
||||||
|
declare ptr @"github.com/goplus/llgo/internal/runtime.IfacePtrData"(%"github.com/goplus/llgo/internal/runtime.iface")
|
||||||
70
cl/_testgo/invoke/in.go
Normal file
70
cl/_testgo/invoke/in.go
Normal file
@@ -0,0 +1,70 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
type T struct {
|
||||||
|
s string
|
||||||
|
}
|
||||||
|
|
||||||
|
func (t T) Invoke() int {
|
||||||
|
println("invoke", t.s)
|
||||||
|
return 0
|
||||||
|
}
|
||||||
|
|
||||||
|
func (t *T) Method() {}
|
||||||
|
|
||||||
|
type T1 int
|
||||||
|
|
||||||
|
func (t T1) Invoke() int {
|
||||||
|
println("invoke1", t)
|
||||||
|
return 1
|
||||||
|
}
|
||||||
|
|
||||||
|
type T2 float64
|
||||||
|
|
||||||
|
func (t T2) Invoke() int {
|
||||||
|
println("invoke2", t)
|
||||||
|
return 2
|
||||||
|
}
|
||||||
|
|
||||||
|
type T3 int8
|
||||||
|
|
||||||
|
func (t *T3) Invoke() int {
|
||||||
|
println("invoke3", *t)
|
||||||
|
return 3
|
||||||
|
}
|
||||||
|
|
||||||
|
type I interface {
|
||||||
|
Invoke() int
|
||||||
|
}
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
var t = T{"hello"}
|
||||||
|
var t1 = T1(100)
|
||||||
|
var t2 = T2(100.1)
|
||||||
|
var t3 = T3(127)
|
||||||
|
invoke(t)
|
||||||
|
invoke(&t)
|
||||||
|
invoke(t1)
|
||||||
|
invoke(&t1)
|
||||||
|
invoke(t2)
|
||||||
|
invoke(&t2)
|
||||||
|
invoke(&t3)
|
||||||
|
var m M
|
||||||
|
var i I = m
|
||||||
|
println(i, m)
|
||||||
|
m = &t
|
||||||
|
invoke(m)
|
||||||
|
var a any = T{"world"}
|
||||||
|
invoke(a.(I))
|
||||||
|
invoke(a.(interface{}).(interface{ Invoke() int }))
|
||||||
|
//panic
|
||||||
|
invoke(nil)
|
||||||
|
}
|
||||||
|
|
||||||
|
func invoke(i I) {
|
||||||
|
println(i.Invoke())
|
||||||
|
}
|
||||||
|
|
||||||
|
type M interface {
|
||||||
|
Invoke() int
|
||||||
|
Method()
|
||||||
|
}
|
||||||
1188
cl/_testgo/invoke/out.ll
Normal file
1188
cl/_testgo/invoke/out.ll
Normal file
File diff suppressed because it is too large
Load Diff
5
cl/_testgo/print/in.go
Normal file
5
cl/_testgo/print/in.go
Normal file
@@ -0,0 +1,5 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
println('.', byte('.'))
|
||||||
|
}
|
||||||
40
cl/_testgo/print/out.ll
Normal file
40
cl/_testgo/print/out.ll
Normal file
@@ -0,0 +1,40 @@
|
|||||||
|
; ModuleID = 'main'
|
||||||
|
source_filename = "main"
|
||||||
|
|
||||||
|
@"main.init$guard" = global ptr null
|
||||||
|
@__llgo_argc = global ptr null
|
||||||
|
@__llgo_argv = global ptr null
|
||||||
|
|
||||||
|
define void @main.init() {
|
||||||
|
_llgo_0:
|
||||||
|
%0 = load i1, ptr @"main.init$guard", align 1
|
||||||
|
br i1 %0, label %_llgo_2, label %_llgo_1
|
||||||
|
|
||||||
|
_llgo_1: ; preds = %_llgo_0
|
||||||
|
store i1 true, ptr @"main.init$guard", align 1
|
||||||
|
br label %_llgo_2
|
||||||
|
|
||||||
|
_llgo_2: ; preds = %_llgo_1, %_llgo_0
|
||||||
|
ret void
|
||||||
|
}
|
||||||
|
|
||||||
|
define i32 @main(i32 %0, ptr %1) {
|
||||||
|
_llgo_0:
|
||||||
|
store i32 %0, ptr @__llgo_argc, align 4
|
||||||
|
store ptr %1, ptr @__llgo_argv, align 8
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
|
call void @main.init()
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintInt"(i64 46)
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintByte"(i8 32)
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintUint"(i64 46)
|
||||||
|
call void @"github.com/goplus/llgo/internal/runtime.PrintByte"(i8 10)
|
||||||
|
ret i32 0
|
||||||
|
}
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.init"()
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.PrintInt"(i64)
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.PrintByte"(i8)
|
||||||
|
|
||||||
|
declare void @"github.com/goplus/llgo/internal/runtime.PrintUint"(i64)
|
||||||
307
cl/_testgo/reader/in.go
Normal file
307
cl/_testgo/reader/in.go
Normal file
@@ -0,0 +1,307 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"unicode/utf8"
|
||||||
|
)
|
||||||
|
|
||||||
|
type Reader interface {
|
||||||
|
Read(p []byte) (n int, err error)
|
||||||
|
}
|
||||||
|
|
||||||
|
type Writer interface {
|
||||||
|
Write(p []byte) (n int, err error)
|
||||||
|
}
|
||||||
|
|
||||||
|
type Closer interface {
|
||||||
|
Close() error
|
||||||
|
}
|
||||||
|
|
||||||
|
type Seeker interface {
|
||||||
|
Seek(offset int64, whence int) (int64, error)
|
||||||
|
}
|
||||||
|
|
||||||
|
type ReadWriter interface {
|
||||||
|
Reader
|
||||||
|
Writer
|
||||||
|
}
|
||||||
|
|
||||||
|
type ReadCloser interface {
|
||||||
|
Reader
|
||||||
|
Closer
|
||||||
|
}
|
||||||
|
|
||||||
|
type WriteCloser interface {
|
||||||
|
Writer
|
||||||
|
Closer
|
||||||
|
}
|
||||||
|
|
||||||
|
type ReadWriteCloser interface {
|
||||||
|
Reader
|
||||||
|
Writer
|
||||||
|
Closer
|
||||||
|
}
|
||||||
|
|
||||||
|
type ReadSeeker interface {
|
||||||
|
Reader
|
||||||
|
Seeker
|
||||||
|
}
|
||||||
|
|
||||||
|
type ReadSeekCloser interface {
|
||||||
|
Reader
|
||||||
|
Seeker
|
||||||
|
Closer
|
||||||
|
}
|
||||||
|
|
||||||
|
type WriteSeeker interface {
|
||||||
|
Writer
|
||||||
|
Seeker
|
||||||
|
}
|
||||||
|
|
||||||
|
type ReadWriteSeeker interface {
|
||||||
|
Reader
|
||||||
|
Writer
|
||||||
|
Seeker
|
||||||
|
}
|
||||||
|
|
||||||
|
type ReaderFrom interface {
|
||||||
|
ReadFrom(r Reader) (n int64, err error)
|
||||||
|
}
|
||||||
|
|
||||||
|
type WriterTo interface {
|
||||||
|
WriteTo(w Writer) (n int64, err error)
|
||||||
|
}
|
||||||
|
|
||||||
|
type ReaderAt interface {
|
||||||
|
ReadAt(p []byte, off int64) (n int, err error)
|
||||||
|
}
|
||||||
|
|
||||||
|
type WriterAt interface {
|
||||||
|
WriteAt(p []byte, off int64) (n int, err error)
|
||||||
|
}
|
||||||
|
|
||||||
|
type ByteReader interface {
|
||||||
|
ReadByte() (byte, error)
|
||||||
|
}
|
||||||
|
|
||||||
|
type ByteScanner interface {
|
||||||
|
ByteReader
|
||||||
|
UnreadByte() error
|
||||||
|
}
|
||||||
|
|
||||||
|
type ByteWriter interface {
|
||||||
|
WriteByte(c byte) error
|
||||||
|
}
|
||||||
|
|
||||||
|
type RuneReader interface {
|
||||||
|
ReadRune() (r rune, size int, err error)
|
||||||
|
}
|
||||||
|
|
||||||
|
type RuneScanner interface {
|
||||||
|
RuneReader
|
||||||
|
UnreadRune() error
|
||||||
|
}
|
||||||
|
|
||||||
|
type StringWriter interface {
|
||||||
|
WriteString(s string) (n int, err error)
|
||||||
|
}
|
||||||
|
|
||||||
|
func WriteString(w Writer, s string) (n int, err error) {
|
||||||
|
if sw, ok := w.(StringWriter); ok {
|
||||||
|
return sw.WriteString(s)
|
||||||
|
}
|
||||||
|
return w.Write([]byte(s))
|
||||||
|
}
|
||||||
|
|
||||||
|
func NopCloser(r Reader) ReadCloser {
|
||||||
|
if _, ok := r.(WriterTo); ok {
|
||||||
|
return nopCloserWriterTo{r}
|
||||||
|
}
|
||||||
|
return nopCloser{r}
|
||||||
|
}
|
||||||
|
|
||||||
|
type nopCloser struct {
|
||||||
|
Reader
|
||||||
|
}
|
||||||
|
|
||||||
|
func (nopCloser) Close() error { return nil }
|
||||||
|
|
||||||
|
type nopCloserWriterTo struct {
|
||||||
|
Reader
|
||||||
|
}
|
||||||
|
|
||||||
|
func (nopCloserWriterTo) Close() error { return nil }
|
||||||
|
|
||||||
|
func (c nopCloserWriterTo) WriteTo(w Writer) (n int64, err error) {
|
||||||
|
return c.Reader.(WriterTo).WriteTo(w)
|
||||||
|
}
|
||||||
|
|
||||||
|
func ReadAll(r Reader) ([]byte, error) {
|
||||||
|
b := make([]byte, 0, 512)
|
||||||
|
for {
|
||||||
|
n, err := r.Read(b[len(b):cap(b)])
|
||||||
|
b = b[:len(b)+n]
|
||||||
|
if err != nil {
|
||||||
|
if err == EOF {
|
||||||
|
err = nil
|
||||||
|
}
|
||||||
|
return b, err
|
||||||
|
}
|
||||||
|
|
||||||
|
if len(b) == cap(b) {
|
||||||
|
// Add more capacity (let append pick how much).
|
||||||
|
b = append(b, 0)[:len(b)]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
type stringReader struct {
|
||||||
|
s string
|
||||||
|
i int64 // current reading index
|
||||||
|
prevRune int // index of previous rune; or < 0
|
||||||
|
}
|
||||||
|
|
||||||
|
func (r *stringReader) Len() int {
|
||||||
|
if r.i >= int64(len(r.s)) {
|
||||||
|
return 0
|
||||||
|
}
|
||||||
|
return int(int64(len(r.s)) - r.i)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (r *stringReader) Size() int64 { return int64(len(r.s)) }
|
||||||
|
|
||||||
|
func (r *stringReader) Read(b []byte) (n int, err error) {
|
||||||
|
if r.i >= int64(len(r.s)) {
|
||||||
|
return 0, EOF
|
||||||
|
}
|
||||||
|
r.prevRune = -1
|
||||||
|
n = copy(b, r.s[r.i:])
|
||||||
|
r.i += int64(n)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
func (r *stringReader) ReadAt(b []byte, off int64) (n int, err error) {
|
||||||
|
if off < 0 {
|
||||||
|
return 0, newError("stringsReader.ReadAt: negative offset")
|
||||||
|
}
|
||||||
|
if off >= int64(len(r.s)) {
|
||||||
|
return 0, EOF
|
||||||
|
}
|
||||||
|
n = copy(b, r.s[off:])
|
||||||
|
if n < len(b) {
|
||||||
|
err = EOF
|
||||||
|
}
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
func (r *stringReader) ReadByte() (byte, error) {
|
||||||
|
r.prevRune = -1
|
||||||
|
if r.i >= int64(len(r.s)) {
|
||||||
|
return 0, EOF
|
||||||
|
}
|
||||||
|
b := r.s[r.i]
|
||||||
|
r.i++
|
||||||
|
return b, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (r *stringReader) UnreadByte() error {
|
||||||
|
if r.i <= 0 {
|
||||||
|
return newError("stringsReader.UnreadByte: at beginning of string")
|
||||||
|
}
|
||||||
|
r.prevRune = -1
|
||||||
|
r.i--
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (r *stringReader) ReadRune() (ch rune, size int, err error) {
|
||||||
|
if r.i >= int64(len(r.s)) {
|
||||||
|
r.prevRune = -1
|
||||||
|
return 0, 0, EOF
|
||||||
|
}
|
||||||
|
r.prevRune = int(r.i)
|
||||||
|
if c := r.s[r.i]; c < utf8.RuneSelf {
|
||||||
|
r.i++
|
||||||
|
return rune(c), 1, nil
|
||||||
|
}
|
||||||
|
ch, size = utf8.DecodeRuneInString(r.s[r.i:])
|
||||||
|
r.i += int64(size)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
func (r *stringReader) UnreadRune() error {
|
||||||
|
if r.i <= 0 {
|
||||||
|
return newError("strings.Reader.UnreadRune: at beginning of string")
|
||||||
|
}
|
||||||
|
if r.prevRune < 0 {
|
||||||
|
return newError("strings.Reader.UnreadRune: previous operation was not ReadRune")
|
||||||
|
}
|
||||||
|
r.i = int64(r.prevRune)
|
||||||
|
r.prevRune = -1
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
const (
|
||||||
|
SeekStart = 0 // seek relative to the origin of the file
|
||||||
|
SeekCurrent = 1 // seek relative to the current offset
|
||||||
|
SeekEnd = 2 // seek relative to the end
|
||||||
|
)
|
||||||
|
|
||||||
|
func (r *stringReader) Seek(offset int64, whence int) (int64, error) {
|
||||||
|
r.prevRune = -1
|
||||||
|
var abs int64
|
||||||
|
switch whence {
|
||||||
|
case SeekStart:
|
||||||
|
abs = offset
|
||||||
|
case SeekCurrent:
|
||||||
|
abs = r.i + offset
|
||||||
|
case SeekEnd:
|
||||||
|
abs = int64(len(r.s)) + offset
|
||||||
|
default:
|
||||||
|
return 0, newError("stringsReader.Seek: invalid whence")
|
||||||
|
}
|
||||||
|
if abs < 0 {
|
||||||
|
return 0, newError("stringsReader.Seek: negative position")
|
||||||
|
}
|
||||||
|
r.i = abs
|
||||||
|
return abs, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (r *stringReader) WriteTo(w Writer) (n int64, err error) {
|
||||||
|
r.prevRune = -1
|
||||||
|
if r.i >= int64(len(r.s)) {
|
||||||
|
return 0, nil
|
||||||
|
}
|
||||||
|
s := r.s[r.i:]
|
||||||
|
m, err := WriteString(w, s)
|
||||||
|
if m > len(s) {
|
||||||
|
panic("stringsReader.WriteTo: invalid WriteString count")
|
||||||
|
}
|
||||||
|
r.i += int64(m)
|
||||||
|
n = int64(m)
|
||||||
|
if m != len(s) && err == nil {
|
||||||
|
err = ErrShortWrite
|
||||||
|
}
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
func newError(text string) error {
|
||||||
|
return &errorString{text}
|
||||||
|
}
|
||||||
|
|
||||||
|
type errorString struct {
|
||||||
|
s string
|
||||||
|
}
|
||||||
|
|
||||||
|
func (e *errorString) Error() string {
|
||||||
|
return e.s
|
||||||
|
}
|
||||||
|
|
||||||
|
var (
|
||||||
|
EOF = newError("EOF")
|
||||||
|
ErrShortWrite = newError("short write")
|
||||||
|
)
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
r := &stringReader{s: "hello world"}
|
||||||
|
data, err := ReadAll(r)
|
||||||
|
println(string(data), err)
|
||||||
|
}
|
||||||
2750
cl/_testgo/reader/out.ll
Normal file
2750
cl/_testgo/reader/out.ll
Normal file
File diff suppressed because it is too large
Load Diff
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user