firefly-compiler 0.5.27 → 0.5.28
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.
- package/compiler/Tokenizer.ff +17 -0
- package/core/Any.ff +30 -30
- package/experimental/random/RunLength.ff +65 -65
- package/output/js/ff/compiler/Tokenizer.mjs +22 -0
- package/output/js/ff/core/Any.mjs +10 -10
- package/package.json +1 -1
- package/vscode/package.json +1 -1
package/compiler/Tokenizer.ff
CHANGED
|
@@ -173,6 +173,23 @@ tokenize(file: String, code: String, completionAt: Option[Location], attemptFixe
|
|
|
173
173
|
|
|
174
174
|
} elseIf {code.grab(i).isAsciiDigit()} {
|
|
175
175
|
|
|
176
|
+
if(i + 2 < code.size() && code.grab(i) == '0' && (
|
|
177
|
+
code.grab(i + 1) == 'x' || code.grab(i + 1) == 'X'
|
|
178
|
+
)) {
|
|
179
|
+
i += 2
|
|
180
|
+
while {i < code.size() && (code.grab(i).isAsciiDigit() || (
|
|
181
|
+
code.grab(i) >= 'a' && code.grab(i) <= 'f'
|
|
182
|
+
) || (
|
|
183
|
+
code.grab(i) >= 'A' && code.grab(i) <= 'F'
|
|
184
|
+
))} {
|
|
185
|
+
i += 1
|
|
186
|
+
}
|
|
187
|
+
if(start == i - 2) {
|
|
188
|
+
throwError("Unexpected character: " + Show.show(code.grab(start + 2)))
|
|
189
|
+
}
|
|
190
|
+
emitToken(LInt, start, i)
|
|
191
|
+
} else:
|
|
192
|
+
|
|
176
193
|
mutable dot = False
|
|
177
194
|
mutable exponent = False
|
|
178
195
|
while {i < code.size() && code.grab(i).isAsciiDigit()} {
|
package/core/Any.ff
CHANGED
|
@@ -1,30 +1,30 @@
|
|
|
1
|
-
data Any {}
|
|
2
|
-
data AnyTag[T] {}
|
|
3
|
-
|
|
4
|
-
trait T: HasAnyTag {
|
|
5
|
-
anyTag(): AnyTag[T]
|
|
6
|
-
}
|
|
7
|
-
|
|
8
|
-
toAny[T: HasAnyTag](value: T): Any
|
|
9
|
-
target js sync """
|
|
10
|
-
const anyTag = ff_core_Any_HasAnyTag$T.anyTag_()
|
|
11
|
-
return {anyTag: anyTag, value: value_}
|
|
12
|
-
"""
|
|
13
|
-
|
|
14
|
-
fromAny[T: HasAnyTag](any: Any): Option[T]
|
|
15
|
-
target js sync """
|
|
16
|
-
const anyTag = ff_core_Any_HasAnyTag$T.anyTag_()
|
|
17
|
-
return any_.anyTag === anyTag ? ff_core_Option.Some(any_.value) : ff_core_Option.None()
|
|
18
|
-
"""
|
|
19
|
-
|
|
20
|
-
extend self[T]: AnyTag[T] {
|
|
21
|
-
show(): String
|
|
22
|
-
target js sync """
|
|
23
|
-
return self_
|
|
24
|
-
"""
|
|
25
|
-
}
|
|
26
|
-
|
|
27
|
-
internalAnyTag[T](tag: String): AnyTag[T]
|
|
28
|
-
target js sync """
|
|
29
|
-
return tag_
|
|
30
|
-
"""
|
|
1
|
+
data Any {}
|
|
2
|
+
data AnyTag[T] {}
|
|
3
|
+
|
|
4
|
+
trait T: HasAnyTag {
|
|
5
|
+
anyTag(): AnyTag[T]
|
|
6
|
+
}
|
|
7
|
+
|
|
8
|
+
toAny[T: HasAnyTag](value: T): Any
|
|
9
|
+
target js sync """
|
|
10
|
+
const anyTag = ff_core_Any_HasAnyTag$T.anyTag_()
|
|
11
|
+
return {anyTag: anyTag, value: value_}
|
|
12
|
+
"""
|
|
13
|
+
|
|
14
|
+
fromAny[T: HasAnyTag](any: Any): Option[T]
|
|
15
|
+
target js sync """
|
|
16
|
+
const anyTag = ff_core_Any_HasAnyTag$T.anyTag_()
|
|
17
|
+
return any_.anyTag === anyTag ? ff_core_Option.Some(any_.value) : ff_core_Option.None()
|
|
18
|
+
"""
|
|
19
|
+
|
|
20
|
+
extend self[T]: AnyTag[T] {
|
|
21
|
+
show(): String
|
|
22
|
+
target js sync """
|
|
23
|
+
return self_
|
|
24
|
+
"""
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
internalAnyTag[T](tag: String): AnyTag[T]
|
|
28
|
+
target js sync """
|
|
29
|
+
return tag_
|
|
30
|
+
"""
|
|
@@ -1,65 +1,65 @@
|
|
|
1
|
-
main(system: NodeSystem) {
|
|
2
|
-
let inBuffers = 1.to(100).map {_ => Buffer.fromByteList([5, 5, 3, 1, 2].toArray())}
|
|
3
|
-
let inStream = inBuffers.toStream()
|
|
4
|
-
let outStream = toRunLength(inStream, 3)
|
|
5
|
-
printRunLength(outStream)
|
|
6
|
-
}
|
|
7
|
-
|
|
8
|
-
printRunLength(outStream: Stream[Buffer]) {
|
|
9
|
-
let buffer = Buffer.fromBufferList(outStream.toArray())
|
|
10
|
-
Log.debug(buffer.toHex())
|
|
11
|
-
let stack = Stack.make()
|
|
12
|
-
mutable i = 0
|
|
13
|
-
while {i < buffer.size()} {
|
|
14
|
-
1.to(buffer.grabUint8(i)).each {_ => stack.push(buffer.grabUint8(i + 1))}
|
|
15
|
-
i += 2
|
|
16
|
-
}
|
|
17
|
-
Log.debug(Buffer.fromByteList(stack.drain()).toHex())
|
|
18
|
-
}
|
|
19
|
-
|
|
20
|
-
toRunLength(stream: Stream[Buffer], bufferSize: Int = 65536): Stream[Buffer] {
|
|
21
|
-
mutable outBuffer = Buffer.new(bufferSize)
|
|
22
|
-
mutable outOffset = 0
|
|
23
|
-
let outBuffers = Stack.make()
|
|
24
|
-
function writeByte(byte: Int): Unit {
|
|
25
|
-
if(outOffset >= outBuffer.size()) {
|
|
26
|
-
outBuffers.push(outBuffer)
|
|
27
|
-
outBuffer = Buffer.new(bufferSize)
|
|
28
|
-
outOffset = 0
|
|
29
|
-
}
|
|
30
|
-
outBuffer.setUint8(outOffset, byte)
|
|
31
|
-
outOffset += 1
|
|
32
|
-
}
|
|
33
|
-
mutable extraCount = 0
|
|
34
|
-
mutable value = 0
|
|
35
|
-
let result = stream.flatMap {inBuffer =>
|
|
36
|
-
mutable i = 0
|
|
37
|
-
while {i < inBuffer.size()} {
|
|
38
|
-
value = if(extraCount > 0) {value} else {inBuffer.grabUint8(i)}
|
|
39
|
-
mutable j = if(extraCount > 0) {-1} else {0}
|
|
40
|
-
doWhile {
|
|
41
|
-
j += 1
|
|
42
|
-
j + extraCount < 256 && i + j < inBuffer.size() && inBuffer.grabUint8(i + j) == value
|
|
43
|
-
}
|
|
44
|
-
i += j
|
|
45
|
-
if(i < inBuffer.size() || j + extraCount == 256) {
|
|
46
|
-
writeByte(j + extraCount)
|
|
47
|
-
writeByte(value)
|
|
48
|
-
extraCount = 0
|
|
49
|
-
} else {
|
|
50
|
-
extraCount += j
|
|
51
|
-
}
|
|
52
|
-
}
|
|
53
|
-
outBuffers.drain().toStream()
|
|
54
|
-
}
|
|
55
|
-
result.addAll(Stream.init {
|
|
56
|
-
if(extraCount > 0) {
|
|
57
|
-
writeByte(extraCount)
|
|
58
|
-
writeByte(value)
|
|
59
|
-
}
|
|
60
|
-
if(outOffset > 0) {
|
|
61
|
-
outBuffers.push(outBuffer.view(0, outOffset))
|
|
62
|
-
}
|
|
63
|
-
outBuffers.drain().toStream()
|
|
64
|
-
})
|
|
65
|
-
}
|
|
1
|
+
main(system: NodeSystem) {
|
|
2
|
+
let inBuffers = 1.to(100).map {_ => Buffer.fromByteList([5, 5, 3, 1, 2].toArray())}
|
|
3
|
+
let inStream = inBuffers.toStream()
|
|
4
|
+
let outStream = toRunLength(inStream, 3)
|
|
5
|
+
printRunLength(outStream)
|
|
6
|
+
}
|
|
7
|
+
|
|
8
|
+
printRunLength(outStream: Stream[Buffer]) {
|
|
9
|
+
let buffer = Buffer.fromBufferList(outStream.toArray())
|
|
10
|
+
Log.debug(buffer.toHex())
|
|
11
|
+
let stack = Stack.make()
|
|
12
|
+
mutable i = 0
|
|
13
|
+
while {i < buffer.size()} {
|
|
14
|
+
1.to(buffer.grabUint8(i)).each {_ => stack.push(buffer.grabUint8(i + 1))}
|
|
15
|
+
i += 2
|
|
16
|
+
}
|
|
17
|
+
Log.debug(Buffer.fromByteList(stack.drain()).toHex())
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
toRunLength(stream: Stream[Buffer], bufferSize: Int = 65536): Stream[Buffer] {
|
|
21
|
+
mutable outBuffer = Buffer.new(bufferSize)
|
|
22
|
+
mutable outOffset = 0
|
|
23
|
+
let outBuffers = Stack.make()
|
|
24
|
+
function writeByte(byte: Int): Unit {
|
|
25
|
+
if(outOffset >= outBuffer.size()) {
|
|
26
|
+
outBuffers.push(outBuffer)
|
|
27
|
+
outBuffer = Buffer.new(bufferSize)
|
|
28
|
+
outOffset = 0
|
|
29
|
+
}
|
|
30
|
+
outBuffer.setUint8(outOffset, byte)
|
|
31
|
+
outOffset += 1
|
|
32
|
+
}
|
|
33
|
+
mutable extraCount = 0
|
|
34
|
+
mutable value = 0
|
|
35
|
+
let result = stream.flatMap {inBuffer =>
|
|
36
|
+
mutable i = 0
|
|
37
|
+
while {i < inBuffer.size()} {
|
|
38
|
+
value = if(extraCount > 0) {value} else {inBuffer.grabUint8(i)}
|
|
39
|
+
mutable j = if(extraCount > 0) {-1} else {0}
|
|
40
|
+
doWhile {
|
|
41
|
+
j += 1
|
|
42
|
+
j + extraCount < 256 && i + j < inBuffer.size() && inBuffer.grabUint8(i + j) == value
|
|
43
|
+
}
|
|
44
|
+
i += j
|
|
45
|
+
if(i < inBuffer.size() || j + extraCount == 256) {
|
|
46
|
+
writeByte(j + extraCount)
|
|
47
|
+
writeByte(value)
|
|
48
|
+
extraCount = 0
|
|
49
|
+
} else {
|
|
50
|
+
extraCount += j
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
outBuffers.drain().toStream()
|
|
54
|
+
}
|
|
55
|
+
result.addAll(Stream.init {
|
|
56
|
+
if(extraCount > 0) {
|
|
57
|
+
writeByte(extraCount)
|
|
58
|
+
writeByte(value)
|
|
59
|
+
}
|
|
60
|
+
if(outOffset > 0) {
|
|
61
|
+
outBuffers.push(outBuffer.view(0, outOffset))
|
|
62
|
+
}
|
|
63
|
+
outBuffers.drain().toStream()
|
|
64
|
+
})
|
|
65
|
+
}
|
|
@@ -254,6 +254,16 @@ emitToken_(ff_compiler_Token.LNamespace(), start_, i_)
|
|
|
254
254
|
emitToken_(kind_, start_, i_)
|
|
255
255
|
}
|
|
256
256
|
} else if(ff_core_Char.Char_isAsciiDigit(ff_core_String.String_grab(code_, i_))) {
|
|
257
|
+
if(((((i_ + 2) < ff_core_String.String_size(code_)) && (ff_core_String.String_grab(code_, i_) === 48)) && ((ff_core_String.String_grab(code_, (i_ + 1)) === 120) || (ff_core_String.String_grab(code_, (i_ + 1)) === 88)))) {
|
|
258
|
+
i_ += 2;
|
|
259
|
+
while(((i_ < ff_core_String.String_size(code_)) && ((ff_core_Char.Char_isAsciiDigit(ff_core_String.String_grab(code_, i_)) || ((ff_core_String.String_grab(code_, i_) >= 97) && (ff_core_String.String_grab(code_, i_) <= 102))) || ((ff_core_String.String_grab(code_, i_) >= 65) && (ff_core_String.String_grab(code_, i_) <= 70))))) {
|
|
260
|
+
i_ += 1
|
|
261
|
+
};
|
|
262
|
+
if((start_ === (i_ - 2))) {
|
|
263
|
+
throwError_(("Unexpected character: " + ff_core_Show.ff_core_Show_Show$ff_core_Char_Char.show_(ff_core_String.String_grab(code_, (start_ + 2)))))
|
|
264
|
+
};
|
|
265
|
+
emitToken_(ff_compiler_Token.LInt(), start_, i_)
|
|
266
|
+
} else {
|
|
257
267
|
let dot_ = false;
|
|
258
268
|
let exponent_ = false;
|
|
259
269
|
while(((i_ < ff_core_String.String_size(code_)) && ff_core_Char.Char_isAsciiDigit(ff_core_String.String_grab(code_, i_)))) {
|
|
@@ -274,6 +284,7 @@ dot_ = true
|
|
|
274
284
|
emitToken_(((dot_ || exponent_)
|
|
275
285
|
? ff_compiler_Token.LFloat()
|
|
276
286
|
: ff_compiler_Token.LInt()), start_, i_)
|
|
287
|
+
}
|
|
277
288
|
} else if((ff_core_String.String_grab(code_, i_) === 95)) {
|
|
278
289
|
i_ += 1;
|
|
279
290
|
emitToken_(ff_compiler_Token.LWildcard(), start_, i_)
|
|
@@ -501,6 +512,16 @@ emitToken_(ff_compiler_Token.LNamespace(), start_, i_)
|
|
|
501
512
|
emitToken_(kind_, start_, i_)
|
|
502
513
|
}
|
|
503
514
|
} else if(ff_core_Char.Char_isAsciiDigit(ff_core_String.String_grab(code_, i_))) {
|
|
515
|
+
if(((((i_ + 2) < ff_core_String.String_size(code_)) && (ff_core_String.String_grab(code_, i_) === 48)) && ((ff_core_String.String_grab(code_, (i_ + 1)) === 120) || (ff_core_String.String_grab(code_, (i_ + 1)) === 88)))) {
|
|
516
|
+
i_ += 2;
|
|
517
|
+
while(((i_ < ff_core_String.String_size(code_)) && ((ff_core_Char.Char_isAsciiDigit(ff_core_String.String_grab(code_, i_)) || ((ff_core_String.String_grab(code_, i_) >= 97) && (ff_core_String.String_grab(code_, i_) <= 102))) || ((ff_core_String.String_grab(code_, i_) >= 65) && (ff_core_String.String_grab(code_, i_) <= 70))))) {
|
|
518
|
+
i_ += 1
|
|
519
|
+
};
|
|
520
|
+
if((start_ === (i_ - 2))) {
|
|
521
|
+
throwError_(("Unexpected character: " + ff_core_Show.ff_core_Show_Show$ff_core_Char_Char.show_(ff_core_String.String_grab(code_, (start_ + 2)))))
|
|
522
|
+
};
|
|
523
|
+
emitToken_(ff_compiler_Token.LInt(), start_, i_)
|
|
524
|
+
} else {
|
|
504
525
|
let dot_ = false;
|
|
505
526
|
let exponent_ = false;
|
|
506
527
|
while(((i_ < ff_core_String.String_size(code_)) && ff_core_Char.Char_isAsciiDigit(ff_core_String.String_grab(code_, i_)))) {
|
|
@@ -521,6 +542,7 @@ dot_ = true
|
|
|
521
542
|
emitToken_(((dot_ || exponent_)
|
|
522
543
|
? ff_compiler_Token.LFloat()
|
|
523
544
|
: ff_compiler_Token.LInt()), start_, i_)
|
|
545
|
+
}
|
|
524
546
|
} else if((ff_core_String.String_grab(code_, i_) === 95)) {
|
|
525
547
|
i_ += 1;
|
|
526
548
|
emitToken_(ff_compiler_Token.LWildcard(), start_, i_)
|
|
@@ -101,22 +101,22 @@ import * as ff_core_UnsafeJs from "../../ff/core/UnsafeJs.mjs"
|
|
|
101
101
|
|
|
102
102
|
|
|
103
103
|
export function toAny_(value_, ff_core_Any_HasAnyTag$T) {
|
|
104
|
-
|
|
105
|
-
const anyTag = ff_core_Any_HasAnyTag$T.anyTag_()
|
|
106
|
-
return {anyTag: anyTag, value: value_}
|
|
104
|
+
|
|
105
|
+
const anyTag = ff_core_Any_HasAnyTag$T.anyTag_()
|
|
106
|
+
return {anyTag: anyTag, value: value_}
|
|
107
107
|
|
|
108
108
|
}
|
|
109
109
|
|
|
110
110
|
export function fromAny_(any_, ff_core_Any_HasAnyTag$T) {
|
|
111
|
-
|
|
112
|
-
const anyTag = ff_core_Any_HasAnyTag$T.anyTag_()
|
|
113
|
-
return any_.anyTag === anyTag ? ff_core_Option.Some(any_.value) : ff_core_Option.None()
|
|
111
|
+
|
|
112
|
+
const anyTag = ff_core_Any_HasAnyTag$T.anyTag_()
|
|
113
|
+
return any_.anyTag === anyTag ? ff_core_Option.Some(any_.value) : ff_core_Option.None()
|
|
114
114
|
|
|
115
115
|
}
|
|
116
116
|
|
|
117
117
|
export function internalAnyTag_(tag_) {
|
|
118
|
-
|
|
119
|
-
return tag_
|
|
118
|
+
|
|
119
|
+
return tag_
|
|
120
120
|
|
|
121
121
|
}
|
|
122
122
|
|
|
@@ -133,8 +133,8 @@ throw new Error('Function internalAnyTag is missing on this target in async cont
|
|
|
133
133
|
}
|
|
134
134
|
|
|
135
135
|
export function AnyTag_show(self_) {
|
|
136
|
-
|
|
137
|
-
return self_
|
|
136
|
+
|
|
137
|
+
return self_
|
|
138
138
|
|
|
139
139
|
}
|
|
140
140
|
|
package/package.json
CHANGED