mirror of
https://github.com/dart-lang/sdk
synced 2024-09-20 05:31:31 +00:00
2dcd56ef43
There are far too many files here to review everyone carefully. Spot checking most of the diffs look good as test code is generally written with less care than application code so lots of ugly formatting get through. If people notice files where the automated formatting bothers them feel free to comment indicating file names and I'll move spaces within comments to make the formatting cleaner and use comments to force block formatting as I have done for other case where formatting looked bad. BUG= R=efortuna@google.com Review-Url: https://codereview.chromium.org/2771453003 .
160 lines
3.8 KiB
Dart
160 lines
3.8 KiB
Dart
// Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file
|
|
// for details. All rights reserved. Use of this source code is governed by a
|
|
// BSD-style license that can be found in the LICENSE file.
|
|
|
|
library MandelIsolateTest;
|
|
|
|
import 'dart:async';
|
|
import 'dart:isolate';
|
|
import 'dart:math';
|
|
import 'package:unittest/unittest.dart';
|
|
import "remote_unittest_helper.dart";
|
|
|
|
const TERMINATION_MESSAGE = -1;
|
|
const N = 100;
|
|
const ISOLATES = 20;
|
|
|
|
void main([args, port]) {
|
|
if (testRemote(main, port)) return;
|
|
// Test is really slow in debug builds of the VM.
|
|
var configuration = unittestConfiguration;
|
|
configuration.timeout = const Duration(seconds: 480);
|
|
test("Render Mandelbrot in parallel", () {
|
|
final state = new MandelbrotState();
|
|
state._validated.future.then(expectAsync((result) {
|
|
expect(result, isTrue);
|
|
}));
|
|
for (int i = 0; i < min(ISOLATES, N); i++) state.startClient(i);
|
|
});
|
|
}
|
|
|
|
class MandelbrotState {
|
|
MandelbrotState() {
|
|
_result = new List<List<int>>(N);
|
|
_lineProcessedBy = new List<LineProcessorClient>(N);
|
|
_sent = 0;
|
|
_missing = N;
|
|
_validated = new Completer<bool>();
|
|
}
|
|
|
|
void startClient(int id) {
|
|
assert(_sent < N);
|
|
int line = _sent++;
|
|
LineProcessorClient.create(this, id).then((final client) {
|
|
client.processLine(line);
|
|
});
|
|
}
|
|
|
|
void notifyProcessedLine(LineProcessorClient client, int y, List<int> line) {
|
|
assert(_result[y] == null);
|
|
_result[y] = line;
|
|
_lineProcessedBy[y] = client;
|
|
|
|
if (_sent != N) {
|
|
client.processLine(_sent++);
|
|
} else {
|
|
client.shutdown();
|
|
}
|
|
|
|
// If all lines have been computed, validate the result.
|
|
if (--_missing == 0) {
|
|
_printResult();
|
|
_validateResult();
|
|
}
|
|
}
|
|
|
|
void _validateResult() {
|
|
// TODO(ngeoffray): Implement this.
|
|
_validated.complete(true);
|
|
}
|
|
|
|
void _printResult() {
|
|
var output = new StringBuffer();
|
|
for (int i = 0; i < _result.length; i++) {
|
|
List<int> line = _result[i];
|
|
for (int j = 0; j < line.length; j++) {
|
|
if (line[j] < 10) output.write("0");
|
|
output.write(line[j]);
|
|
}
|
|
output.write("\n");
|
|
}
|
|
// print(output);
|
|
}
|
|
|
|
List<List<int>> _result;
|
|
List<LineProcessorClient> _lineProcessedBy;
|
|
int _sent;
|
|
int _missing;
|
|
Completer<bool> _validated;
|
|
}
|
|
|
|
class LineProcessorClient {
|
|
MandelbrotState _state;
|
|
int _id;
|
|
SendPort _port;
|
|
|
|
LineProcessorClient(this._state, this._id, this._port);
|
|
|
|
static Future<LineProcessorClient> create(MandelbrotState state, int id) {
|
|
ReceivePort reply = new ReceivePort();
|
|
return Isolate.spawn(processLines, reply.sendPort).then((_) {
|
|
return reply.first.then((port) {
|
|
return new LineProcessorClient(state, id, port);
|
|
});
|
|
});
|
|
}
|
|
|
|
void processLine(int y) {
|
|
ReceivePort reply = new ReceivePort();
|
|
_port.send([y, reply.sendPort]);
|
|
reply.first.then((List<int> message) {
|
|
_state.notifyProcessedLine(this, y, message);
|
|
});
|
|
}
|
|
|
|
void shutdown() {
|
|
_port.send(TERMINATION_MESSAGE);
|
|
}
|
|
}
|
|
|
|
List<int> processLine(int y) {
|
|
double inverseN = 2.0 / N;
|
|
double Civ = y * inverseN - 1.0;
|
|
List<int> result = new List<int>(N);
|
|
for (int x = 0; x < N; x++) {
|
|
double Crv = x * inverseN - 1.5;
|
|
|
|
double Zrv = Crv;
|
|
double Ziv = Civ;
|
|
|
|
double Trv = Crv * Crv;
|
|
double Tiv = Civ * Civ;
|
|
|
|
int i = 49;
|
|
do {
|
|
Ziv = (Zrv * Ziv) + (Zrv * Ziv) + Civ;
|
|
Zrv = Trv - Tiv + Crv;
|
|
|
|
Trv = Zrv * Zrv;
|
|
Tiv = Ziv * Ziv;
|
|
} while (((Trv + Tiv) <= 4.0) && (--i > 0));
|
|
|
|
result[x] = i;
|
|
}
|
|
return result;
|
|
}
|
|
|
|
void processLines(SendPort replyPort) {
|
|
ReceivePort port = new ReceivePort();
|
|
port.listen((message) {
|
|
if (message != TERMINATION_MESSAGE) {
|
|
int line = message[0];
|
|
SendPort replyTo = message[1];
|
|
replyTo.send(processLine(line));
|
|
} else {
|
|
port.close();
|
|
}
|
|
});
|
|
replyPort.send(port.sendPort);
|
|
}
|