Skip to content

Commit c193d9f

Browse files
JasperGeurtzdgant
authored andcommitted
remove parallel tests and replace memcpy with unsafe.copyMemory
1 parent e76bed2 commit c193d9f

File tree

5 files changed

+42
-90
lines changed

5 files changed

+42
-90
lines changed

pom.xml

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -60,12 +60,12 @@
6060
<groupId>org.apache.maven.plugins</groupId>
6161
<artifactId>maven-surefire-plugin</artifactId>
6262
<version>2.22.0</version>
63-
<configuration>
64-
<parallel>all</parallel> <!-- Run tests in parallel-->
65-
<useUnlimitedThreads>true</useUnlimitedThreads>
66-
<argLine>-Xms1g</argLine>
67-
<argLine>-Xmx1g</argLine>
68-
</configuration>
63+
<!-- <configuration>-->
64+
<!-- <parallel>all</parallel> &lt;!&ndash; Run tests in parallel&ndash;&gt;-->
65+
<!-- <useUnlimitedThreads>true</useUnlimitedThreads>-->
66+
<!-- <argLine>-Xms1g</argLine>-->
67+
<!-- <argLine>-Xmx1g</argLine>-->
68+
<!-- </configuration>-->
6969
</plugin>
7070
<plugin>
7171
<groupId>org.codehaus.mojo</groupId>

src/main/java/bwapi/FrameBuffer.java

Lines changed: 10 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,7 @@
11
package bwapi;
22

3-
import com.sun.jna.Platform;
4-
import sun.nio.ch.DirectBuffer;
5-
import java.nio.ByteBuffer;
3+
import sun.misc.Unsafe;
4+
65
import java.util.ArrayList;
76
import java.util.concurrent.locks.Condition;
87
import java.util.concurrent.locks.Lock;
@@ -13,6 +12,7 @@
1312
*/
1413
class FrameBuffer {
1514
private static final int BUFFER_SIZE = ClientData.GameData.SIZE;
15+
private static final Unsafe unsafe = UnsafeTools.getUnsafe();
1616

1717
private WrappedBuffer liveData;
1818
private PerformanceMetrics performanceMetrics;
@@ -158,24 +158,11 @@ void dequeue() {
158158
* @param source Address to copy from
159159
* @param destination Address to copy to
160160
* @param size Number of bytes to copy
161-
* @return True if the copy succeeded
162161
*/
163-
private boolean tryMemcpyBuffer(WrappedBuffer source, WrappedBuffer destination, long offset, int size) {
162+
private void copyBuffer(WrappedBuffer source, WrappedBuffer destination, long offset, int size) {
164163
long addressSource = source.getAddress() + offset;
165164
long addressDestination = destination.getAddress() + offset;
166-
try {
167-
if (Platform.isWindows()) {
168-
if (Platform.is64Bit()) {
169-
MSVCRT.INSTANCE.memcpy(addressDestination, addressSource, size);
170-
return true;
171-
} else {
172-
MSVCRT.INSTANCE.memcpy((int) addressDestination, (int) addressSource, size);
173-
return true;
174-
}
175-
}
176-
}
177-
catch(Exception ignored) {}
178-
return false;
165+
unsafe.copyMemory(addressSource, addressDestination, size);
179166
}
180167

181168
void copyBuffer(WrappedBuffer source, WrappedBuffer destination, boolean copyEverything) {
@@ -185,16 +172,10 @@ void copyBuffer(WrappedBuffer source, WrappedBuffer destination, boolean copyEve
185172
but are prone to large amounts of variance.
186173
187174
The normal Java way to execute this copy is via ByteBuffer.put(), which has reasonably good performance characteristics.
188-
Experiments in 64-bit JRE have shown that using a native memcpy achieves a 35% speedup.
189-
Experiments in 32-bit JRE show no difference in performance.
190-
191-
So, speculatively, we attempt to do a native memcpy.
192175
*/
193176

194177
if (copyEverything) {
195-
if (tryMemcpyBuffer(source, destination, 0, FrameBuffer.BUFFER_SIZE)) {
196-
return;
197-
}
178+
copyBuffer(source, destination, 0, FrameBuffer.BUFFER_SIZE);
198179
} else {
199180
// After the buffer has been filled the first time,
200181
// we can omit copying blocks of data which are unused or which don't change after game start.
@@ -207,18 +188,10 @@ void copyBuffer(WrappedBuffer source, WrappedBuffer destination, boolean copyEve
207188
final int STRINGSSHAPES_START = 10962632; // getStringCount, ... getShapes
208189
final int STRINGSHAPES_END = 32242636;
209190
final int UNITFINDER_START = 32962644;
210-
if (
211-
tryMemcpyBuffer(source, destination, 0, STATICTILES_START)
212-
&& tryMemcpyBuffer(source, destination, STATICTILES_END, REGION_START - STATICTILES_END)
213-
&& tryMemcpyBuffer(source, destination, REGION_END, STRINGSSHAPES_START - REGION_END)
214-
&& tryMemcpyBuffer(source, destination, STRINGSHAPES_END, UNITFINDER_START - STRINGSHAPES_END)) {
215-
return;
216-
}
191+
copyBuffer(source, destination, 0, STATICTILES_START);
192+
copyBuffer(source, destination, STATICTILES_END, REGION_START - STATICTILES_END);
193+
copyBuffer(source, destination, REGION_END, STRINGSSHAPES_START - REGION_END);
194+
copyBuffer(source, destination, STRINGSHAPES_END, UNITFINDER_START - STRINGSHAPES_END);
217195
}
218-
219-
// There's no specific case where we expect to fail above,
220-
// but this is a safe fallback regardless,
221-
// and serves to document the known-good (and cross-platform, for BWAPI 5) way to executing the copy.
222-
destination.copyFrom(source);
223196
}
224197
}

src/main/java/bwapi/MSVCRT.java

Lines changed: 0 additions & 27 deletions
This file was deleted.

src/main/java/bwapi/UnsafeTools.java

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
package bwapi;
2+
3+
import sun.misc.Unsafe;
4+
5+
import java.lang.reflect.Field;
6+
7+
class UnsafeTools {
8+
private static Unsafe unsafe;
9+
10+
static {
11+
try {
12+
final Field theUnsafe = Unsafe.class.getDeclaredField("theUnsafe");
13+
theUnsafe.setAccessible(true);
14+
unsafe = (Unsafe) theUnsafe.get(null);
15+
16+
} catch (final Exception e) {
17+
e.printStackTrace();
18+
System.exit(-1);
19+
}
20+
}
21+
22+
static Unsafe getUnsafe() {
23+
return unsafe;
24+
}
25+
}

src/main/java/bwapi/WrappedBuffer.java

Lines changed: 1 addition & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,6 @@
44
import com.sun.jna.Pointer;
55
import sun.misc.Unsafe;
66

7-
import java.lang.reflect.Field;
87
import java.nio.ByteBuffer;
98

109
/**
@@ -14,19 +13,7 @@ class WrappedBuffer {
1413
private final ByteBuffer buffer;
1514
private final long address;
1615

17-
private static Unsafe unsafe;
18-
19-
static {
20-
try {
21-
final Field theUnsafe = Unsafe.class.getDeclaredField("theUnsafe");
22-
theUnsafe.setAccessible(true);
23-
unsafe = (Unsafe) theUnsafe.get(null);
24-
25-
} catch (final Exception e) {
26-
e.printStackTrace();
27-
System.exit(-1);
28-
}
29-
}
16+
private static final Unsafe unsafe = UnsafeTools.getUnsafe();
3017

3118
WrappedBuffer(final int size) {
3219
this(new Memory(size), size);
@@ -37,12 +24,6 @@ class WrappedBuffer {
3724
this.address = Pointer.nativeValue(pointer);
3825
}
3926

40-
void copyFrom(WrappedBuffer source) {
41-
source.buffer.rewind();
42-
buffer.rewind();
43-
buffer.put(source.buffer);
44-
}
45-
4627
byte getByte(final int offset) {
4728
return unsafe.getByte(address + offset);
4829
}

0 commit comments

Comments
 (0)