Skip to content

Commit

Permalink
add pnacl support for ceval
Browse files Browse the repository at this point in the history
  • Loading branch information
niklasf authored and ornicar committed Oct 2, 2016
1 parent 1739bab commit 1421952
Show file tree
Hide file tree
Showing 7 changed files with 194 additions and 144 deletions.
4 changes: 4 additions & 0 deletions .gitmodules
Original file line number Diff line number Diff line change
Expand Up @@ -44,3 +44,7 @@
path = public/vendor/Sunsetter8
url = https://github.com/niklasf/Sunsetter8
branch = js
[submodule "public/vendor/stockfish.pexe"]
path = public/vendor/stockfish.pexe
url = https://github.com/niklasf/stockfish.pexe
branch = ddugovic
1 change: 1 addition & 0 deletions public/vendor/stockfish.pexe
Submodule stockfish.pexe added at 6e0738
25 changes: 17 additions & 8 deletions ui/analyse/src/ceval/cevalCtrl.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,8 @@ var m = require('mithril');
var makePool = require('./cevalPool');
var dict = require('./cevalDict');
var util = require('../util');
var stockfishWorker = require('./stockfishWorker');
var sunsetterWorker = require('./sunsetterWorker');
var stockfishProtocol = require('./stockfishProtocol');
var sunsetterProtocol = require('./sunsetterProtocol');

module.exports = function(possible, variant, emit) {

Expand All @@ -16,13 +16,22 @@ module.exports = function(possible, variant, emit) {
var allowed = m.prop(true);
var enabled = m.prop(possible() && allowed() && lichess.storage.get(storageKey) === '1');
var started = false;
var engine = variant.key !== 'crazyhouse' ? stockfishWorker : sunsetterWorker;

var pool = makePool({
minDepth: minDepth,
maxDepth: maxDepth,
variant: variant
}, engine, nbWorkers);
var pool;
if (variant.key !== 'crazyhouse') {
pool = makePool(stockfishProtocol, {
asmjs: '/assets/vendor/stockfish.js/stockfish.js',
pnacl: '/assets/vendor/stockfish.pexe/nacl/stockfish.nmf'
}, {
minDepth: minDepth,
maxDepth: maxDepth,
variant: variant,
});
} else {
pool = makePool(sunsetterProtocol, {
asmjs: '/assets/vendor/Sunsetter8/sunsetter.js'
});
}

// adjusts maxDepth based on nodes per second
var npsRecorder = (function() {
Expand Down
70 changes: 66 additions & 4 deletions ui/analyse/src/ceval/cevalPool.js
Original file line number Diff line number Diff line change
@@ -1,7 +1,65 @@
var m = require('mithril');

module.exports = function(opts, makeWorker, nb) {
function makeHelper(makeWorker, terminateWorker, poolOpts, makeProtocol, protocolOpts) {
var worker, protocol, api;

var boot = function () {
worker = makeWorker(poolOpts);
protocol = makeProtocol(api, protocolOpts);
worker.addEventListener('message', function(e) {
protocol.received(e.data);
}, true);
};

var stop = function() {
var stopped = m.deferred(false);
setTimeout(function () {
stopped.reject();
}, 1000);
return protocol.stop(stopped);
};

api = {
send: function(text) {
worker.postMessage(text);
},
start: function (work) {
stop().then(function () {
protocol.start(work);
}, function () {
terminateWorker(worker);
boot();
});
},
stop: stop
};

boot();

return api;
}

function makeWebWorker(makeProtocol, poolOpts, protocolOpts) {
return makeHelper(function () {
return new Worker(poolOpts.asmjs);
}, function (worker) {
worker.terminate();
}, poolOpts, makeProtocol, protocolOpts);
}

function makePNaClModule(makeProtocol, poolOpts, protocolOpts) {
return makeHelper(function () {
var module = document.createElement('embed');
module.setAttribute('src', poolOpts.pnacl);
module.setAttribute('type', 'application/x-pnacl');
module.setAttribute('width', '0');
module.setAttribute('height', '0');
document.body.appendChild(module);
return module;
}, function () {}, poolOpts, makeProtocol, protocolOpts);
}

module.exports = function(makeProtocol, poolOpts, protocolOpts) {
var workers = [];
var token = -1;

Expand All @@ -12,9 +70,13 @@ module.exports = function(opts, makeWorker, nb) {
};

var initWorkers = function() {
if (!workers.length)
for (var i = 1; i <= nb; i++)
workers.push(makeWorker(opts, 'W' + i));
if (workers.length) return;

if (poolOpts.pnacl && navigator.mimeTypes['application/x-pnacl'])
workers.push(makePNaClModule(makeProtocol, poolOpts, protocolOpts));
else
for (var i = 1; i <= 4; i++)
workers.push(makeWebWorker(makeProtocol, poolOpts, protocolOpts));
}

var stopAll = function() {
Expand Down
75 changes: 75 additions & 0 deletions ui/analyse/src/ceval/stockfishProtocol.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
var m = require('mithril');

var legacyVariantMap = {
fromPosition: 'Chess960',
chess960: 'Chess960',
atomic: 'Atomic',
horde: 'Horde',
crazyhouse: 'House',
kingOfTheHill: 'KingOfTheHill',
racingKings: 'Race',
threeCheck: '3Check',
antichess: 'Anti'
};

module.exports = function(worker, opts) {

var work = null;
var stopped = m.deferred();

var legacyVariant = legacyVariantMap[opts.variant.key];
if (legacyVariant) worker.send('setoption name UCI_' + legacyVariant + ' value true');
else worker.send('uci');

// TODO: Modern variant selector

var processOutput = function(text) {
if (text.indexOf('bestmove ') === 0) {
stopped.resolve(true);
return;
}
if (!work) return;
if (/currmovenumber|lowerbound|upperbound/.test(text)) return;
var matches = text.match(/depth (\d+) .*score (cp|mate) ([-\d]+) .*nps (\d+) .*pv (.+)/);
if (!matches) return;
var depth = parseInt(matches[1]);
if (depth < opts.minDepth) return;
var cp, mate;
if (matches[2] === 'cp') cp = parseFloat(matches[3]);
else mate = parseFloat(matches[3]);
if (work.ply % 2 === 1) {
if (matches[2] === 'cp') cp = -cp;
else mate = -mate;
}
var best = matches[5].split(' ')[0];
work.emit({
work: work,
eval: {
depth: depth,
cp: cp,
mate: mate,
best: best,
nps: parseInt(matches[4])
},
name: name
});
};

return {
start: function(w) {
work = w;
worker.send(['position', 'fen', work.initialFen, 'moves'].concat(work.moves).join(' '));
worker.send('go depth ' + work.maxDepth);
},
stop: function(s) {
if (!work) s.resolve(true);
else {
work = null;
stopped = s;
worker.send('stop');
}
return s.promise;
},
received: processOutput
};
};
86 changes: 0 additions & 86 deletions ui/analyse/src/ceval/stockfishWorker.js

This file was deleted.

Loading

0 comments on commit 1421952

Please sign in to comment.