My Project
|
Parallel search. More...
#include "ybwc.h"
#include "move.h"
#include "options.h"
#include "util.h"
#include "search.h"
#include "stats.h"
#include "settings.h"
#include <assert.h>
#include <stdlib.h>
Functions | |
void | node_init (Node *node, Search *search, const int alpha, const int beta, const int depth, const int n_moves, Node *parent) |
Initialize a node. More... | |
void | node_free (Node *node) |
Free Resources allocated by a node. More... | |
static bool | get_helper (Node *master, Node *node, Move *move) |
Seek for & use an helper node. More... | |
bool | node_split (Node *node, Move *move) |
Node split. More... | |
void | node_wait_slaves (Node *node) |
Wait for slaves termination. More... | |
void | node_update (Node *node, Move *move) |
Update a node. More... | |
Move * | node_first_move (Node *node, MoveList *movelist) |
Get the first move of the move list. More... | |
static Move * | node_next_move_lockless (Node *node) |
Get the next move of the move list. More... | |
Move * | node_next_move (Node *node) |
Get the next move of the move list. More... | |
void | task_search (Task *task) |
A parallel search within a Task structure. More... | |
void * | task_loop (void *param) |
The main loop runned by a task. More... | |
static Search * | task_search_create (Task *task) |
Create a search structure for a task. More... | |
static void | task_search_destroy (Search *search) |
Free a search structure of a task. More... | |
void | task_init (Task *task) |
Initialize a task. More... | |
void | task_free (Task *task) |
Free resources used by a task. More... | |
void | task_stack_init (TaskStack *stack, const int n) |
Initialize the stack of tasks. More... | |
void | task_stack_free (TaskStack *stack) |
Free resources used by the stack of tasks. More... | |
void | task_stack_resize (TaskStack *stack, const int n) |
Resize the stack of tasks. More... | |
Task * | task_stack_get_idle_task (TaskStack *stack) |
Return, if available, an idle task. More... | |
void | task_stack_put_idle_task (TaskStack *stack, Task *task) |
Put back an idle task after using it. More... | |
Variables | |
Log | search_log [1] |
Parallel search.
The Young Brother Wait Concept [1, 2] is an efficient technique to search a position with several cpu/core working in parallel. At an inner nodes, this technique always evaluates the first move using a sequential approach, but try to evaluate the siblings in parallel, once the first move has been computed. The YBWC has some nice properties: low search overhead, good scalability, easy implementation, etc.
This file holds the function definition to manipulate structures used in our implementation of parallelism:
References:
Seek for & use an helper node.
When asking for an idle task, this function look if a parent node is waiting and has a task available to help the current search.
master | A parent node with an idle task. |
node | Searched node. |
move | Searched move. |
Get the first move of the move list.
This is thread/safe getter of the first move. If the search is stopped, or an alphabeta cut has been found or no move is available the function returns NULL.
node | Node data. |
movelist | List of moves. |
void node_init | ( | Node * | node, |
Search * | search, | ||
const int | alpha, | ||
const int | beta, | ||
const int | depth, | ||
const int | n_moves, | ||
Node * | parent | ||
) |
Initialize a node.
Initialize the various members of the node structure. The important part of the initialization establishes a master-slave relashionship between this node (the slave) and its parent (the master).
node | A potentially shared position. |
search | The position searched |
alpha | lower score bound. |
beta | upper score bound. |
depth | depth. |
n_moves | Move count. |
parent | The parent node. |
Get the next move of the move list.
This is a thread/safe getter of the next move.
node | Node data. |
Get the next move of the move list.
This is a thread/safe getter of the next move. If the search is stopped, or an alphabeta cut has been found or no move is available the function returns NULL.
node | Node data. |
Node split.
Here is the heart of the YBWC algorithm. It splits a node into two tasks. Splitting occurs if the following conditions are met:
node | Master node to split. |
move | move to search. |
Update a node.
Update bestmove, bestscore and alpha value of the node, in case the move is the bestmove found so far. The function is thread-safe although it updates a shared resource. Double check lock is used as an optimization.
node | current node. |
move | last evaluated move. |
void node_wait_slaves | ( | Node * | node | ) |
Wait for slaves termination.
Actually, three steps are performed here:
node | Node. |
void task_free | ( | Task * | task | ) |
Free resources used by a task.
task | The task. |
void task_init | ( | Task * | task | ) |
Initialize a task.
Initialize task data members and start the task main loop task_loop() within a thread.
task | The task. |
void * task_loop | ( | void * | param | ) |
The main loop runned by a task.
When task->run is set to true, the task starts a parallel search. In order to diminish the parallelism overhead, we do not launch a new thread at each new splitted node. Instead the threads are created at the beginning of the program and run a waiting loop who enters/quits a parallel search when requested.
param | The task. |
void task_search | ( | Task * | task | ) |
A parallel search within a Task structure.
Here we share the search with a main parent task.
task | The task to search with. |
Create a search structure for a task.
task | The task. |
|
static |
Free a search structure of a task.
search | The search structure. |
void task_stack_free | ( | TaskStack * | stack | ) |
Free resources used by the stack of tasks.
stack | The stack of tasks. |
Return, if available, an idle task.
stack | The stack of tasks. |
void task_stack_init | ( | TaskStack * | stack, |
const int | n | ||
) |
Initialize the stack of tasks.
stack | The stack of tasks. |
n | Stack size (number of tasks). |
Put back an idle task after using it.
stack | The stack of tasks. |
task | An idle task. |
void task_stack_resize | ( | TaskStack * | stack, |
const int | n | ||
) |
Resize the stack of tasks.
stack | Stack to resize. |
n | New stack size. |
|
extern |