Skip to content

Commit d7fb520

Browse files
committed
implement FPDP
1 parent e6d940d commit d7fb520

File tree

3 files changed

+177
-0
lines changed

3 files changed

+177
-0
lines changed

src/main/java/com/falsepattern/jfunge/interpreter/instructions/Funge98.java

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22

33
import com.falsepattern.jfunge.Globals;
44
import com.falsepattern.jfunge.interpreter.ExecutionContext;
5+
import com.falsepattern.jfunge.interpreter.instructions.fingerprints.FPDP;
56
import com.falsepattern.jfunge.interpreter.instructions.fingerprints.FPSP;
67
import com.falsepattern.jfunge.interpreter.instructions.fingerprints.HRTI;
78
import com.falsepattern.jfunge.interpreter.instructions.fingerprints.MODE;
@@ -43,6 +44,7 @@ public class Funge98 implements InstructionSet {
4344
static {
4445
addFingerprint(_3DSP.INSTANCE);
4546
addFingerprint(FPSP.INSTANCE);
47+
addFingerprint(FPDP.INSTANCE);
4648
addFingerprint(HRTI.INSTANCE);
4749
addFingerprint(MODE.INSTANCE);
4850
addFingerprint(MODU.INSTANCE);
Lines changed: 158 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,158 @@
1+
package com.falsepattern.jfunge.interpreter.instructions.fingerprints;
2+
3+
import com.falsepattern.jfunge.interpreter.ExecutionContext;
4+
import com.falsepattern.jfunge.interpreter.instructions.Fingerprint;
5+
import gnu.trove.function.TDoubleFunction;
6+
import lombok.AccessLevel;
7+
import lombok.NoArgsConstructor;
8+
import lombok.SneakyThrows;
9+
import lombok.val;
10+
import org.joml.Math;
11+
12+
import java.nio.charset.StandardCharsets;
13+
import java.text.DecimalFormat;
14+
15+
@NoArgsConstructor(access = AccessLevel.PRIVATE)
16+
public class FPDP implements Fingerprint {
17+
public static final FPDP INSTANCE = new FPDP();
18+
@Override
19+
public int code() {
20+
return 0x46504450;
21+
}
22+
23+
private interface BinOp {
24+
double op(double a, double b);
25+
}
26+
27+
private static void binop(ExecutionContext ctx, BinOp op) {
28+
val stack = ctx.stack();
29+
val b = stack.popD();
30+
val a = stack.popD();
31+
stack.pushD(op.op(a, b));
32+
}
33+
34+
private static void unop(ExecutionContext ctx, TDoubleFunction op) {
35+
val stack = ctx.stack();
36+
stack.pushD(op.execute(stack.popD()));
37+
}
38+
39+
@Instr('A')
40+
public static void add(ExecutionContext ctx) {
41+
binop(ctx, Double::sum);
42+
}
43+
44+
@Instr('B')
45+
public static void sin(ExecutionContext ctx) {
46+
unop(ctx, Math::sin);
47+
}
48+
49+
@Instr('C')
50+
public static void cos(ExecutionContext ctx) {
51+
unop(ctx, Math::cos);
52+
}
53+
54+
@Instr('D')
55+
public static void div(ExecutionContext ctx) {
56+
binop(ctx, (a, b) -> a / b);
57+
}
58+
59+
@Instr('E')
60+
public static void aSin(ExecutionContext ctx) {
61+
unop(ctx, Math::asin);
62+
}
63+
64+
@Instr('F')
65+
public static void iToF(ExecutionContext ctx) {
66+
val stack = ctx.stack();
67+
stack.pushD(stack.pop());
68+
}
69+
70+
@Instr('G')
71+
public static void atan(ExecutionContext ctx) {
72+
unop(ctx, java.lang.Math::atan);
73+
}
74+
75+
@Instr('H')
76+
public static void acos(ExecutionContext ctx) {
77+
unop(ctx, Math::acos);
78+
}
79+
80+
@Instr('I')
81+
public static void fToI(ExecutionContext ctx) {
82+
val stack = ctx.stack();
83+
stack.push((int)stack.popD());
84+
}
85+
86+
@Instr('K')
87+
public static void logE(ExecutionContext ctx) {
88+
unop(ctx, java.lang.Math::log);
89+
}
90+
91+
@Instr('L')
92+
public static void log10(ExecutionContext ctx) {
93+
unop(ctx, java.lang.Math::log10);
94+
}
95+
96+
@Instr('M')
97+
public static void mul(ExecutionContext ctx) {
98+
binop(ctx, (a, b) -> a * b);
99+
}
100+
101+
@Instr('N')
102+
public static void negate(ExecutionContext ctx) {
103+
unop(ctx, (x) -> -x);
104+
}
105+
106+
private static final DecimalFormat PRINT_FORMAT = new DecimalFormat("0.###### ");
107+
108+
@SneakyThrows
109+
@Instr('P')
110+
public static void print(ExecutionContext ctx) {
111+
ctx.output()
112+
.write(PRINT_FORMAT.format(ctx.stack().popD())
113+
.replace("\uFFFD", "NaN ")
114+
.replace("\u221E", "infinity")
115+
.getBytes(StandardCharsets.UTF_8));
116+
}
117+
118+
@Instr('Q')
119+
public static void sqrt(ExecutionContext ctx) {
120+
unop(ctx, Math::sqrt);
121+
}
122+
123+
@Instr('R')
124+
public static void parseDouble(ExecutionContext ctx) {
125+
val stack = ctx.stack();
126+
val str = stack.popString();
127+
try {
128+
stack.pushD(Double.parseDouble(str));
129+
} catch (NumberFormatException e) {
130+
ctx.interpret('r');
131+
}
132+
}
133+
134+
@Instr('S')
135+
public static void sub(ExecutionContext ctx) {
136+
binop(ctx, (a, b) -> a - b);
137+
}
138+
139+
@Instr('T')
140+
public static void tan(ExecutionContext ctx) {
141+
unop(ctx, Math::tan);
142+
}
143+
144+
@Instr('V')
145+
public static void abs(ExecutionContext ctx) {
146+
unop(ctx, Math::abs);
147+
}
148+
149+
@Instr('X')
150+
public static void exp(ExecutionContext ctx) {
151+
unop(ctx, Math::exp);
152+
}
153+
154+
@Instr('Y')
155+
public static void pow(ExecutionContext ctx) {
156+
binop(ctx, java.lang.Math::pow);
157+
}
158+
}

src/main/java/com/falsepattern/jfunge/ip/IStack.java

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -122,6 +122,15 @@ default String popString() {
122122
return data.toString("UTF-8");
123123
}
124124

125+
default void pushL(long value) {
126+
push((int) (value & 0xFFFFFFFFL));
127+
push((int) ((value >> 32) & 0xFFFFFFFFL));
128+
}
129+
130+
default long popL() {
131+
return ((long) pop() << 32) | (pop() & 0xFFFFFFFFL);
132+
}
133+
125134
default void pushF(float val) {
126135
push(Float.floatToRawIntBits(val));
127136
}
@@ -130,6 +139,14 @@ default float popF() {
130139
return Float.intBitsToFloat(pop());
131140
}
132141

142+
default void pushD(double val) {
143+
pushL(Double.doubleToRawLongBits(val));
144+
}
145+
146+
default double popD() {
147+
return Double.longBitsToDouble(popL());
148+
}
149+
133150
default void pushF2(Vector2fc v) {
134151
pushF(v.x());
135152
pushF(v.y());

0 commit comments

Comments
 (0)