spitewaste 0.2.01 → 0.2.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/lib/spitewaste.rb +4 -0
- data/lib/spitewaste/emitters/image.rb +1 -1
- data/lib/spitewaste/libspw/array.spw +4 -5
- data/lib/spitewaste/libspw/docs.json +289 -13
- data/lib/spitewaste/libspw/fun.spw +14 -0
- data/lib/spitewaste/libspw/io.spw +13 -11
- data/lib/spitewaste/libspw/random.spw +5 -0
- data/lib/spitewaste/libspw/stack.spw +11 -0
- data/lib/spitewaste/libspw/string.spw +22 -0
- data/lib/spitewaste/libspw/util.spw +30 -2
- data/lib/spitewaste/parsers/spitewaste.rb +4 -2
- data/lib/spitewaste/version.rb +1 -1
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: f039f7e3e393fc05321b8eec880b0596320a5a2bf6edc5bd6690502db221fd25
|
4
|
+
data.tar.gz: d2e137737cf57c865637b0ab44a9fe2546c141e8dec624865c7932553b81ceee
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 34cc5fa69d331f4d227b0c7a4263b64fd87464bc52d5aae87bd41012e8d92b825891e779b7620aa8e885c39178d7f983f4e8dc7beb7b6e23d22e834dba08b8f7
|
7
|
+
data.tar.gz: 92b0baacda3b6030e41f49c8915598bfb3d40e7f7fc13ee204aa0a9c8f2696840cea36e834f765fcba8fcbdaaf872cedf65689f6804580847b6e08cbe6387271
|
data/lib/spitewaste.rb
CHANGED
@@ -112,7 +112,7 @@ module Spitewaste
|
|
112
112
|
flow: %i[jump jz jn ret exit],
|
113
113
|
math: %i[add sub mul div mod],
|
114
114
|
heap: %i[store load],
|
115
|
-
io: %i[ichr inum ochr onum],
|
115
|
+
io: %i[ichr inum ochr onum shell],
|
116
116
|
calls: %i[call label]
|
117
117
|
}.flat_map { |type, insns| insns.map { |i| [i, type] } }.to_h
|
118
118
|
|
@@ -219,11 +219,10 @@ _sorted_yes: push 1 slide 3 ret
|
|
219
219
|
; [1 2 3 3] => [3 2 1 3]
|
220
220
|
; [7 1] => [7 1]
|
221
221
|
; [5 4 3 2 1 5] => [1 2 3 4 5 5]
|
222
|
-
aryrev:
|
223
|
-
|
224
|
-
|
225
|
-
|
226
|
-
push 3 sub load ret
|
222
|
+
aryrev:
|
223
|
+
push -10 :aryheap push -10
|
224
|
+
@-9 times (dup load swap $--)
|
225
|
+
pop @-9 ret
|
227
226
|
|
228
227
|
; returns the array A replicated N times
|
229
228
|
; ! N must be greater than 1
|
@@ -1455,6 +1455,53 @@
|
|
1455
1455
|
}
|
1456
1456
|
},
|
1457
1457
|
"fun": {
|
1458
|
+
"ROT13": {
|
1459
|
+
"full": "applies the ROT13 \"cipher\" to the string S\n[S] => [S']\n\n[\"gnat\"] => [\"tang\"]\n[\"purely\"] => [\"cheryl\"]\n[\"cat.PNG\"] => [\"png.CAT\"]\n[\"Hello, world.\"] => [\"Uryyb, jbeyq.\"]\n[\"a123z\"] => [\"n123m\"]\n",
|
1460
|
+
"desc": "applies the ROT13 \"cipher\" to the string S",
|
1461
|
+
"effect": "[S] => [S']",
|
1462
|
+
"cases": [
|
1463
|
+
[
|
1464
|
+
[
|
1465
|
+
244873063
|
1466
|
+
],
|
1467
|
+
[
|
1468
|
+
217821428
|
1469
|
+
]
|
1470
|
+
],
|
1471
|
+
[
|
1472
|
+
[
|
1473
|
+
4186733066992
|
1474
|
+
],
|
1475
|
+
[
|
1476
|
+
3743573177443
|
1477
|
+
]
|
1478
|
+
],
|
1479
|
+
[
|
1480
|
+
[
|
1481
|
+
314962935099619
|
1482
|
+
],
|
1483
|
+
[
|
1484
|
+
371687373272944
|
1485
|
+
]
|
1486
|
+
],
|
1487
|
+
[
|
1488
|
+
[
|
1489
|
+
905009539406525881141375688
|
1490
|
+
],
|
1491
|
+
[
|
1492
|
+
906989270706565425435408725
|
1493
|
+
]
|
1494
|
+
],
|
1495
|
+
[
|
1496
|
+
[
|
1497
|
+
32856905953
|
1498
|
+
],
|
1499
|
+
[
|
1500
|
+
29367245038
|
1501
|
+
]
|
1502
|
+
]
|
1503
|
+
]
|
1504
|
+
},
|
1458
1505
|
"anagrams?": {
|
1459
1506
|
"full": "returns whether the strings S and T are composed of the same characters\n[S T] => [0 | 1]\n\n[\"allergy\" \"gallery\"] => [1]\n[\"largely\" \"regally\"] => [1]\n[\"foo\" \"bar\"] => [0]\n",
|
1460
1507
|
"desc": "returns whether the strings S and T are composed of the same characters",
|
@@ -1699,33 +1746,49 @@
|
|
1699
1746
|
},
|
1700
1747
|
"io": {
|
1701
1748
|
"getline": {
|
1702
|
-
"full": "reads a line of input onto the top of the stack as a packed string\n",
|
1703
|
-
"desc": "",
|
1704
|
-
"effect": "
|
1749
|
+
"full": "reads a line of input onto the top of the stack as a packed string\n[] => [L]\n",
|
1750
|
+
"desc": "reads a line of input onto the top of the stack as a packed string",
|
1751
|
+
"effect": "[] => [L]",
|
1705
1752
|
"cases": [
|
1706
1753
|
|
1707
1754
|
]
|
1708
1755
|
},
|
1709
1756
|
"print": {
|
1710
|
-
"full": "prints the character at the top of the stack until terminating zero\n",
|
1711
|
-
"desc": "",
|
1712
|
-
"effect": "
|
1757
|
+
"full": "prints the character at the top of the stack until terminating zero\n[0 ... C] => []\n",
|
1758
|
+
"desc": "prints the character at the top of the stack until terminating zero",
|
1759
|
+
"effect": "[0 ... C] => []",
|
1713
1760
|
"cases": [
|
1714
1761
|
|
1715
1762
|
]
|
1716
1763
|
},
|
1717
1764
|
"println": {
|
1718
|
-
"full": "print with newline\n",
|
1719
|
-
"desc": "",
|
1720
|
-
"effect": "
|
1765
|
+
"full": "print with newline\n[0 ... C] => []\n",
|
1766
|
+
"desc": "print with newline",
|
1767
|
+
"effect": "[0 ... C] => []",
|
1768
|
+
"cases": [
|
1769
|
+
|
1770
|
+
]
|
1771
|
+
},
|
1772
|
+
"prompt": {
|
1773
|
+
"full": "displays the string S then reads a line of input\n[S] => [L]\n",
|
1774
|
+
"desc": "displays the string S then reads a line of input",
|
1775
|
+
"effect": "[S] => [L]",
|
1721
1776
|
"cases": [
|
1722
1777
|
|
1723
1778
|
]
|
1724
1779
|
},
|
1725
1780
|
"readall": {
|
1726
|
-
"full": "consume stdin until EOF\n",
|
1727
|
-
"desc": "",
|
1728
|
-
"effect": "
|
1781
|
+
"full": "consume stdin until EOF into the string S\n[] => [S]\n",
|
1782
|
+
"desc": "consume stdin until EOF into the string S",
|
1783
|
+
"effect": "[] => [S]",
|
1784
|
+
"cases": [
|
1785
|
+
|
1786
|
+
]
|
1787
|
+
},
|
1788
|
+
"readfile": {
|
1789
|
+
"full": "returns the contents C of the file at path P (a string)\nNON-STANDARD! This function makes use of the `shell` instruction, which is\nonly(?) available in the Spiceweight Whitespace interpreter.\n[P] => [C]\n",
|
1790
|
+
"desc": "returns the contents C of the file at path P (a string)\nNON-STANDARD! This function makes use of the `shell` instruction, which is\nonly(?) available in the Spiceweight Whitespace interpreter.",
|
1791
|
+
"effect": "[P] => [C]",
|
1729
1792
|
"cases": [
|
1730
1793
|
|
1731
1794
|
]
|
@@ -2564,6 +2627,14 @@
|
|
2564
2627
|
}
|
2565
2628
|
},
|
2566
2629
|
"random": {
|
2630
|
+
"bogosort": {
|
2631
|
+
"full": "sorts the array A if you're lucky\n[A] => [A']\n",
|
2632
|
+
"desc": "sorts the array A if you're lucky",
|
2633
|
+
"effect": "[A] => [A']",
|
2634
|
+
"cases": [
|
2635
|
+
|
2636
|
+
]
|
2637
|
+
},
|
2567
2638
|
"dice": {
|
2568
2639
|
"full": "returns an array A of N random integers between 1 and D (inclusive)\n[N D] => [A]\n",
|
2569
2640
|
"desc": "returns an array A of N random integers between 1 and D (inclusive)",
|
@@ -3668,6 +3739,93 @@
|
|
3668
3739
|
]
|
3669
3740
|
]
|
3670
3741
|
},
|
3742
|
+
"swapary": {
|
3743
|
+
"full": "swaps the two arrays at the top of the stack\n[A B] => [B A]\n\n[1 2 3 3 3 2 1 3] => [3 2 1 3 1 2 3 3]\n[5 6 2 9 7 5 3 1 5] => [9 7 5 3 1 5 5 6 2]\n[0 0 2 4 2 0 3] => [4 2 0 3 0 0 2]\n[1 1 2 1] => [2 1 1 1]\n",
|
3744
|
+
"desc": "swaps the two arrays at the top of the stack",
|
3745
|
+
"effect": "[A B] => [B A]",
|
3746
|
+
"cases": [
|
3747
|
+
[
|
3748
|
+
[
|
3749
|
+
1,
|
3750
|
+
2,
|
3751
|
+
3,
|
3752
|
+
3,
|
3753
|
+
3,
|
3754
|
+
2,
|
3755
|
+
1,
|
3756
|
+
3
|
3757
|
+
],
|
3758
|
+
[
|
3759
|
+
3,
|
3760
|
+
2,
|
3761
|
+
1,
|
3762
|
+
3,
|
3763
|
+
1,
|
3764
|
+
2,
|
3765
|
+
3,
|
3766
|
+
3
|
3767
|
+
]
|
3768
|
+
],
|
3769
|
+
[
|
3770
|
+
[
|
3771
|
+
5,
|
3772
|
+
6,
|
3773
|
+
2,
|
3774
|
+
9,
|
3775
|
+
7,
|
3776
|
+
5,
|
3777
|
+
3,
|
3778
|
+
1,
|
3779
|
+
5
|
3780
|
+
],
|
3781
|
+
[
|
3782
|
+
9,
|
3783
|
+
7,
|
3784
|
+
5,
|
3785
|
+
3,
|
3786
|
+
1,
|
3787
|
+
5,
|
3788
|
+
5,
|
3789
|
+
6,
|
3790
|
+
2
|
3791
|
+
]
|
3792
|
+
],
|
3793
|
+
[
|
3794
|
+
[
|
3795
|
+
0,
|
3796
|
+
0,
|
3797
|
+
2,
|
3798
|
+
4,
|
3799
|
+
2,
|
3800
|
+
0,
|
3801
|
+
3
|
3802
|
+
],
|
3803
|
+
[
|
3804
|
+
4,
|
3805
|
+
2,
|
3806
|
+
0,
|
3807
|
+
3,
|
3808
|
+
0,
|
3809
|
+
0,
|
3810
|
+
2
|
3811
|
+
]
|
3812
|
+
],
|
3813
|
+
[
|
3814
|
+
[
|
3815
|
+
1,
|
3816
|
+
1,
|
3817
|
+
2,
|
3818
|
+
1
|
3819
|
+
],
|
3820
|
+
[
|
3821
|
+
2,
|
3822
|
+
1,
|
3823
|
+
1,
|
3824
|
+
1
|
3825
|
+
]
|
3826
|
+
]
|
3827
|
+
]
|
3828
|
+
},
|
3671
3829
|
"to_a": {
|
3672
3830
|
"full": "pops elements off the stack until it hits the specified sentinel value S,\npushing them to the resulting pseudo-array. It's often more convenient to\nbuild up a collection in reverse order, and we often don't know in advance\nhow many elements we'll meet, but we do know to stop at the sentinel.\n[S En ... E1 S] => [E1 ... En n]\n\n[-1 9 8 7 -1] => [7 8 9 3]\n[0 'c' 'b' 'a' 0] => ['a' 'b' 'c' 3]\n",
|
3673
3831
|
"desc": "pops elements off the stack until it hits the specified sentinel value S,\npushing them to the resulting pseudo-array. It's often more convenient to\nbuild up a collection in reverse order, and we often don't know in advance\nhow many elements we'll meet, but we do know to stop at the sentinel.",
|
@@ -4103,6 +4261,49 @@
|
|
4103
4261
|
]
|
4104
4262
|
]
|
4105
4263
|
},
|
4264
|
+
"strbegins?": {
|
4265
|
+
"full": "returns 1 if the string S begins with substring T, 0 otherwise\n[S T] => [0 | 1]\n\n[\"foobar\" \"foo\"] => [1]\n[\"foobar\" \"boo\"] => [0]\n[\"abc123\" \"123\"] => [0]\n[\" foo\" \" \"] = [1]\n",
|
4266
|
+
"desc": "returns 1 if the string S begins with substring T, 0 otherwise",
|
4267
|
+
"effect": "[S T] => [0 | 1]",
|
4268
|
+
"cases": [
|
4269
|
+
[
|
4270
|
+
[
|
4271
|
+
3943255767014,
|
4272
|
+
1832934
|
4273
|
+
],
|
4274
|
+
[
|
4275
|
+
1
|
4276
|
+
]
|
4277
|
+
],
|
4278
|
+
[
|
4279
|
+
[
|
4280
|
+
3943255767014,
|
4281
|
+
1832930
|
4282
|
+
],
|
4283
|
+
[
|
4284
|
+
0
|
4285
|
+
]
|
4286
|
+
],
|
4287
|
+
[
|
4288
|
+
[
|
4289
|
+
1765872824673,
|
4290
|
+
842033
|
4291
|
+
],
|
4292
|
+
[
|
4293
|
+
0
|
4294
|
+
]
|
4295
|
+
],
|
4296
|
+
[
|
4297
|
+
[
|
4298
|
+
234615584,
|
4299
|
+
32
|
4300
|
+
],
|
4301
|
+
[
|
4302
|
+
1
|
4303
|
+
]
|
4304
|
+
]
|
4305
|
+
]
|
4306
|
+
},
|
4106
4307
|
"strcat": {
|
4107
4308
|
"full": "takes two packed strings and returns their concatenation (as a packed string)\n[S T] => [S+T]\n\n[\"foo\" \"\"] => [\"foo\"]\n[\"\" \"foo\"] => [\"foo\"]\n[\"foo\" \"bar\"] => [\"foobar\"]\n",
|
4108
4309
|
"desc": "takes two packed strings and returns their concatenation (as a packed string)",
|
@@ -4314,6 +4515,49 @@
|
|
4314
4515
|
]
|
4315
4516
|
]
|
4316
4517
|
},
|
4518
|
+
"strends?": {
|
4519
|
+
"full": "returns 1 if the string S ends with substring T, 0 otherwise\n[S T] => [0 | 1]\n\n[\"foobar\" \"bar\"] => [1]\n[\"foobar\" \"foo\"] => [0]\n[\"abc123\" \"abc\"] => [0]\n[\"foo \" \" \"] = [1]\n",
|
4520
|
+
"desc": "returns 1 if the string S ends with substring T, 0 otherwise",
|
4521
|
+
"effect": "[S T] => [0 | 1]",
|
4522
|
+
"cases": [
|
4523
|
+
[
|
4524
|
+
[
|
4525
|
+
3943255767014,
|
4526
|
+
1880290
|
4527
|
+
],
|
4528
|
+
[
|
4529
|
+
1
|
4530
|
+
]
|
4531
|
+
],
|
4532
|
+
[
|
4533
|
+
[
|
4534
|
+
3943255767014,
|
4535
|
+
1832934
|
4536
|
+
],
|
4537
|
+
[
|
4538
|
+
0
|
4539
|
+
]
|
4540
|
+
],
|
4541
|
+
[
|
4542
|
+
[
|
4543
|
+
1765872824673,
|
4544
|
+
1634657
|
4545
|
+
],
|
4546
|
+
[
|
4547
|
+
0
|
4548
|
+
]
|
4549
|
+
],
|
4550
|
+
[
|
4551
|
+
[
|
4552
|
+
68941798,
|
4553
|
+
32
|
4554
|
+
],
|
4555
|
+
[
|
4556
|
+
1
|
4557
|
+
]
|
4558
|
+
]
|
4559
|
+
]
|
4560
|
+
},
|
4317
4561
|
"strexpand": {
|
4318
4562
|
"full": "expands the length-2 string S to contain the intervening ASCII characters\n[S] => [S']\n\n[\"CJ\"] => [\"CDEFGHIJ\"]\n[\"DA\"] => [\"DCBA\"]\n[\"af\"] => [\"abcdef\"]\n[\"09\"] => [\"0123456789\"]\n[\"90\"] => [\"9876543210\"]\n[\"(1\"] => [\"()*+,-./01\"]\n",
|
4319
4563
|
"desc": "expands the length-2 string S to contain the intervening ASCII characters",
|
@@ -5035,6 +5279,14 @@
|
|
5035
5279
|
|
5036
5280
|
]
|
5037
5281
|
},
|
5282
|
+
"aryheap": {
|
5283
|
+
"full": "stashes the array A in negative heap space starting at index I\n[A I] => []\n",
|
5284
|
+
"desc": "stashes the array A in negative heap space starting at index I",
|
5285
|
+
"effect": "[A I] => []",
|
5286
|
+
"cases": [
|
5287
|
+
|
5288
|
+
]
|
5289
|
+
},
|
5038
5290
|
"between?": {
|
5039
5291
|
"full": "returns 1 if the number N is between A and B (inclusive), 0 otherwise\n[N A B]\n\n[5 0 10] => [1]\n[11 0 10] => [0]\n[4 0 4] => [1]\n[-1 0 4] => [0]\n[-5 -10 0] => [1]\n[3 4 2] => [0]\n",
|
5040
5292
|
"desc": "returns 1 if the number N is between A and B (inclusive), 0 otherwise",
|
@@ -5315,7 +5567,7 @@
|
|
5315
5567
|
]
|
5316
5568
|
]
|
5317
5569
|
},
|
5318
|
-
"
|
5570
|
+
"heap-seeking_missile": {
|
5319
5571
|
"full": "Though extremely rare, it's possible that we know a particular value is\nstored in the heap at some key, just not which one. This subroutine takes\na value V to search for and a starting index I, and either returns the first\nkey associated with that value or loops forever. Probably don't touch.\n[V I]\n",
|
5320
5572
|
"desc": "Though extremely rare, it's possible that we know a particular value is\nstored in the heap at some key, just not which one. This subroutine takes\na value V to search for and a starting index I, and either returns the first\nkey associated with that value or loops forever. Probably don't touch.",
|
5321
5573
|
"effect": "[V I]",
|
@@ -5323,6 +5575,22 @@
|
|
5323
5575
|
|
5324
5576
|
]
|
5325
5577
|
},
|
5578
|
+
"heapary": {
|
5579
|
+
"full": "restores the heaped array starting at index I\n[I] => [A]\n",
|
5580
|
+
"desc": "restores the heaped array starting at index I",
|
5581
|
+
"effect": "[I] => [A]",
|
5582
|
+
"cases": [
|
5583
|
+
|
5584
|
+
]
|
5585
|
+
},
|
5586
|
+
"heapswap": {
|
5587
|
+
"full": "swaps the elements in the heap at indices I and J\n[I J] => []\n",
|
5588
|
+
"desc": "swaps the elements in the heap at indices I and J",
|
5589
|
+
"effect": "[I J] => []",
|
5590
|
+
"cases": [
|
5591
|
+
|
5592
|
+
]
|
5593
|
+
},
|
5326
5594
|
"hex2rgb": {
|
5327
5595
|
"full": "converts the #RRGGBB (leading '#' optional) color string S to\nits individual RGB components as integers in the range 0-255\n[S] => [R G B]\n\n[\"#000000\"] => [0 0 0]\n[\"ffffff\"] => [255 255 255]\n[\"#102030\"] => [16 32 48]\n[\"c0ffee\"] => [192 255 238]\n",
|
5328
5596
|
"desc": "converts the #RRGGBB (leading '#' optional) color string S to\nits individual RGB components as integers in the range 0-255",
|
@@ -5998,6 +6266,14 @@
|
|
5998
6266
|
]
|
5999
6267
|
]
|
6000
6268
|
]
|
6269
|
+
},
|
6270
|
+
"time": {
|
6271
|
+
"full": "returns the number of nanoseconds N since the Unix epoch\n[] => [N]\n",
|
6272
|
+
"desc": "returns the number of nanoseconds N since the Unix epoch",
|
6273
|
+
"effect": "[] => [N]",
|
6274
|
+
"cases": [
|
6275
|
+
|
6276
|
+
]
|
6001
6277
|
}
|
6002
6278
|
}
|
6003
6279
|
}
|
@@ -94,3 +94,17 @@ to_roman: push -2,0 store
|
|
94
94
|
$_to_roman("X", 10) $_to_roman("IX", 9)
|
95
95
|
$_to_roman("V", 5) $_to_roman("IV", 4)
|
96
96
|
$_to_roman("I", 1) push 2 sub load ret
|
97
|
+
|
98
|
+
; applies the ROT13 "cipher" to the string S
|
99
|
+
; [S] => [S']
|
100
|
+
;
|
101
|
+
; ["gnat"] => ["tang"]
|
102
|
+
; ["purely"] => ["cheryl"]
|
103
|
+
; ["cat.PNG"] => ["png.CAT"]
|
104
|
+
; ["Hello, world."] => ["Uryyb, jbeyq."]
|
105
|
+
; ["a123z"] => ["n123m"]
|
106
|
+
ROT13:
|
107
|
+
push "AZ" :strexpand push "az" :strexpand :strcat
|
108
|
+
push "NZ" :strexpand push "AM" :strexpand
|
109
|
+
push "nz" :strexpand push "am" :strexpand
|
110
|
+
:strcat :strcat :strcat :strtrans ret
|
@@ -1,6 +1,7 @@
|
|
1
1
|
import string ; strcat, strpack, strrev, strunpack
|
2
2
|
|
3
3
|
; prints the character at the top of the stack until terminating zero
|
4
|
+
; [0 ... C] => []
|
4
5
|
print: :strunpack
|
5
6
|
_print_loop:
|
6
7
|
dup jz _print_done
|
@@ -8,34 +9,35 @@ _print_loop:
|
|
8
9
|
_print_done: pop ret
|
9
10
|
|
10
11
|
; print with newline
|
12
|
+
; [0 ... C] => []
|
11
13
|
println: :print push 10 ochr ret
|
12
14
|
|
13
|
-
;;;
|
14
|
-
|
15
15
|
; reads a line of input onto the top of the stack as a packed string
|
16
16
|
; ! clobbers heap address -1
|
17
|
+
; [] => [L]
|
17
18
|
getline: push 0 ; terminator for strpack
|
18
|
-
|
19
|
-
; read characters onto the stack until newline (10) or EOF (-1)
|
20
19
|
_getline_loop:
|
21
20
|
push -1 dup ichr load
|
22
21
|
dup jn _getline_eof
|
23
22
|
dup push 10 sub jz _getline_done
|
24
23
|
jump _getline_loop
|
25
|
-
|
26
24
|
_getline_eof: pop
|
27
25
|
_getline_done: :strpack :strrev ret
|
28
26
|
|
29
|
-
|
30
|
-
|
27
|
+
; displays the string S then reads a line of input
|
28
|
+
; [S] => [L]
|
31
29
|
prompt: :print :getline ret
|
32
30
|
|
33
|
-
|
34
|
-
|
35
|
-
; consume stdin until EOF
|
31
|
+
; consume stdin until EOF into the string S
|
32
|
+
; [] => [S]
|
36
33
|
readall: push 0 ; accumulated string
|
37
34
|
_readall_loop:
|
38
35
|
:getline dup jz _readall_done
|
39
36
|
:strcat jump _readall_loop
|
40
|
-
|
41
37
|
_readall_done: pop ret
|
38
|
+
|
39
|
+
; returns the contents C of the file at path P (a string)
|
40
|
+
; NON-STANDARD! This function makes use of the `shell` instruction, which is
|
41
|
+
; only(?) available in the Spiceweight Whitespace interpreter.
|
42
|
+
; [P] => [C]
|
43
|
+
readfile: push "cat " swap :strcat shell ret
|
@@ -1,3 +1,4 @@
|
|
1
|
+
import array ; sorted?
|
1
2
|
import math ; pow
|
2
3
|
import string ; strtoa
|
3
4
|
|
@@ -32,3 +33,7 @@ _shuffle_loop:
|
|
32
33
|
; shuffles the characters of the string S, producing a random anagram
|
33
34
|
; [S] => [S']
|
34
35
|
strfry: :strtoa :shuffle pop :strpack ret
|
36
|
+
|
37
|
+
; sorts the array A if you're lucky
|
38
|
+
; [A] => [A']
|
39
|
+
bogosort: :shuffle :arydup :sorted? jz bogosort ret
|
@@ -104,3 +104,14 @@ _ncopy_restore:
|
|
104
104
|
dup push 9 add jz _ncopy_done
|
105
105
|
dup load swap push 1 add jump _ncopy_restore
|
106
106
|
_ncopy_done: pop ret
|
107
|
+
|
108
|
+
; swaps the two arrays at the top of the stack
|
109
|
+
; [A B] => [B A]
|
110
|
+
;
|
111
|
+
; [1 2 3 3 3 2 1 3] => [3 2 1 3 1 2 3 3]
|
112
|
+
; [5 6 2 9 7 5 3 1 5] => [9 7 5 3 1 5 5 6 2]
|
113
|
+
; [0 0 2 4 2 0 3] => [4 2 0 3 0 0 2]
|
114
|
+
; [1 1 2 1] => [2 1 1 1]
|
115
|
+
swapary:
|
116
|
+
push -10 :aryheap push -11 @-9 sub :aryheap
|
117
|
+
push -10 :heapary push -11 @-9 sub :heapary ret
|
@@ -399,3 +399,25 @@ strtoa: dup :strlen pop :strunpack @-1 $++ ret
|
|
399
399
|
; ["foobar"] => ["LEEHKX"]
|
400
400
|
; ["LEEHKX"] => ["foobar"]
|
401
401
|
memfrob: :strtoa map (push 42 :bxor) pop :strpack ret
|
402
|
+
|
403
|
+
; returns 1 if the string S begins with substring T, 0 otherwise
|
404
|
+
; [S T] => [0 | 1]
|
405
|
+
;
|
406
|
+
; ["foobar" "foo"] => [1]
|
407
|
+
; ["foobar" "boo"] => [0]
|
408
|
+
; ["abc123" "123"] => [0]
|
409
|
+
; [" foo" " "] = [1]
|
410
|
+
strbegins?:
|
411
|
+
dup :strlen copy 2 swap push 0 swap
|
412
|
+
:strslice :eq slide 1 ret
|
413
|
+
|
414
|
+
; returns 1 if the string S ends with substring T, 0 otherwise
|
415
|
+
; [S T] => [0 | 1]
|
416
|
+
;
|
417
|
+
; ["foobar" "bar"] => [1]
|
418
|
+
; ["foobar" "foo"] => [0]
|
419
|
+
; ["abc123" "abc"] => [0]
|
420
|
+
; ["foo " " "] = [1]
|
421
|
+
strends?:
|
422
|
+
:strrev dup :strlen copy 2 :strrev swap push 0 swap
|
423
|
+
:strslice :eq slide 1 ret
|
@@ -215,8 +215,8 @@ between?: copy 2 :gte swap copy 2 :lte mul slide 1 ret
|
|
215
215
|
; a value V to search for and a starting index I, and either returns the first
|
216
216
|
; key associated with that value or loops forever. Probably don't touch.
|
217
217
|
; [V I]
|
218
|
-
|
219
|
-
$++ dup load copy 2 :eq jz
|
218
|
+
heap-seeking_missile:
|
219
|
+
$++ dup load copy 2 :eq jz heap-seeking_missile
|
220
220
|
slide 1 ret
|
221
221
|
|
222
222
|
; converts the #RRGGBB (leading '#' optional) color string S to
|
@@ -246,3 +246,31 @@ rgb2hex:
|
|
246
246
|
copy 2 push 256 mul add add
|
247
247
|
slide 2 :to_hex push 6,48 :rjustc ret
|
248
248
|
_rgb2hex_invalid: push "(rgb2hex) invalid RGB" :die!
|
249
|
+
|
250
|
+
; stashes the array A in negative heap space starting at index I
|
251
|
+
; [A I] => []
|
252
|
+
aryheap:
|
253
|
+
$++ dup copy 2 store
|
254
|
+
swap times ($-- swap copy 1 swap store) pop ret
|
255
|
+
|
256
|
+
; restores the heaped array starting at index I
|
257
|
+
; [I] => [A]
|
258
|
+
heapary:
|
259
|
+
$++ dup load swap copy 1 sub swap
|
260
|
+
times (dup load swap $++) load ret
|
261
|
+
|
262
|
+
; swaps the elements in the heap at indices I and J
|
263
|
+
; ! TODO: make heap effects doctest-able
|
264
|
+
; [I J] => []
|
265
|
+
heapswap: dup load swap copy 2 load store store ret
|
266
|
+
|
267
|
+
; returns the number of nanoseconds N since the Unix epoch
|
268
|
+
; [] => [N]
|
269
|
+
time: push "date +%s%N" shell :to_i ret
|
270
|
+
|
271
|
+
$bench(insns) {
|
272
|
+
#insns :println
|
273
|
+
:time ^0 `insns` :time @0 sub
|
274
|
+
push 10,9 :pow :divmod swap onum
|
275
|
+
push '.' ochr :to_s push 9,48 :rjustc :println
|
276
|
+
}
|
@@ -148,11 +148,13 @@ module Spitewaste
|
|
148
148
|
params, body = @macros[$1]
|
149
149
|
raise "no macro function '#$1'" unless body
|
150
150
|
map = parse[params].zip(parse[$2]).to_h
|
151
|
-
body
|
151
|
+
body
|
152
|
+
.gsub(/`(.+?)`/) { map[$1] }
|
153
|
+
.gsub(/#(\S+)/) { "push #{Spitewaste.strpack map[$1]}" }
|
152
154
|
}
|
153
155
|
|
154
156
|
@src.gsub!(/(\$\S+)\s*=\s*(.+)/) { @macros[$1] ||= $2; '' }
|
155
|
-
@src.gsub!(/(
|
157
|
+
@src.gsub!(/(\$[^)\s]+)/) { @macros[$1] || raise("no macro '#$1'") }
|
156
158
|
end
|
157
159
|
|
158
160
|
def eliminate_dead_code!
|
data/lib/spitewaste/version.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: spitewaste
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.2.
|
4
|
+
version: 0.2.2
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Collided Scope (collidedscope)
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2021-01-
|
11
|
+
date: 2021-01-08 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: rake
|