import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Scanner;

public class D_5 {
	public static void main(String[] args) throws Exception {
		new D_5().go();
	}

	int USE_FILE = 3;
	String INPUT = "4\r\n" +
			"4 3 2 1 2\r\n" +
			"1 2\r\n" +
			"1 3\r\n" +
			"1 4\r\n" +
			"6 6 1 2 5\r\n" +
			"1 2\r\n" +
			"6 5\r\n" +
			"2 3\r\n" +
			"3 4\r\n" +
			"4 5\r\n" +
			"9 3 9 2 5\r\n" +
			"1 2\r\n" +
			"1 6\r\n" +
			"1 9\r\n" +
			"1 3\r\n" +
			"9 5\r\n" +
			"7 9\r\n" +
			"4 8\r\n" +
			"4 3\r\n" +
			"11 8 11 3 3\r\n" +
			"1 2\r\n" +
			"11 9\r\n" +
			"4 9\r\n" +
			"6 5\r\n" +
			"2 10\r\n" +
			"3 2\r\n" +
			"5 9\r\n" +
			"8 3\r\n" +
			"7 4\r\n" +
			"7 10";

	void solve(int caseNr) {
		int n = in.nextInt();
		int a = in.nextInt();
		int b = in.nextInt();
		int da = in.nextInt();
		int db = in.nextInt();

		nodes = new Node[n+1];

		for (int i = 1; i < n+1; i++) {
			nodes[i] = new Node(i);
		}

		for (int i = 1; i <= n-1; i++) {
			int n1 = in.nextInt();
			int n2 = in.nextInt();
			// System.out.printf("(%d %d) \n", n1, n2);
			nodes[n1].c.add(nodes[n2]);
			nodes[n2].c.add(nodes[n1]);
		}

		// This method will find the tree-diameter starting from any node
		findDepth(1);
		findDepth(deepest_node.id);

		int tree_diameter = max_distance;

		findDistance(a,b);
		// System.out.println(ab_distance);

		//		for (int i = 1; i <= n; i++) {
		//			findDepth(i);
		//			findDepth(deepest_node.id);
		//			System.out.println(max_distance);
		//		}
		//		for (int i = 1; i <= n; i++) {
		//			findDistance(7,i);
		//			System.out.printf("distance from 8 to %2d = %4d\n", i, ab_distance);
		//		}

		//		out.printf("n=%d a=%d b=%d da=%d db=%d \n", n, a, b, da, db);
		//		for (int i = 1; i <= n; i++) {
		//			nodes[i].sortChildren();
		//			out.println(nodes[i]);
		//		}

		//		if (caseNr == 2 && print_wrong) {
		//			out.println("Bob");
		//			print_wrong = false;
		//			return;
		//		}

		if (ab_distance <= da) {
			out.println("Alice");
			return;
		}
		if (2*da >= tree_diameter) {
			out.println("Alice");
			return;
		}
		if (db <= 2*da) {
			out.println("Alice");
			return;
		}
		out.println("Bob");

		return;
	} // end of solve2

	// these are unchanged
	Node[] nodes = null;

	// visit must be reset for dfs and bfs traversals
	boolean[] visited = null;

	// these are set when doing getDepth(..)
	Node deepest_node;
	int max_distance;

	// these are set when searching for the distance to a target node
	int ab_distance;
	int target_node;
	boolean search_done = false;

	void findDistance(int n1, int n2) {
		int n = nodes.length;
		visited = new boolean[n+1];
		ab_distance = 0;
		target_node = n2;
		search_done = false;
		distance(nodes[n1], 0);
	}

	void distance(Node n, int depth) {
		if (search_done) return;
		visited[n.id] = true;

		if (n.id == target_node) {
			ab_distance = depth;
			search_done = true;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			distance(nod, depth+1);
		}
	}

	// gets depth and assigns deepest_node
	void findDepth(int node_id) {
		int n = nodes.length;
		visited = new boolean[n+1];
		deepest_node = nodes[node_id];
		depth(nodes[node_id], 0);
	}

	void depth(Node n, int depth) {
		visited[n.id] = true;

		// System.out.println(depth);
		// System.out.println("n.id = "+n.id);

		if (depth > max_distance) {
			max_distance = depth;
			deepest_node = n;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			depth(nod, depth+1);
		}
	}

	class Node implements Comparable<Node> {
		int id;
		List<Node> c = new ArrayList<>();

		public Node(int id) {
			this.id = id;
		}

		@Override
		public String toString() {
			String str_rtn = "";
			for (Node n : c) {
				str_rtn += String.format("%d > %d    ", id, n.id);
			}
			return str_rtn;
		}

		public void sortChildren() {
			Collections.sort(c);
		}

		@Override
		public int compareTo(Node n2) {
			return this.id - n2.id;
		}
	}

	// ---------------------------------------------------------------------------------------------- //

	boolean HAS_TESTCASES = true;
	void testCases() {
		int t = 1;
		if (HAS_TESTCASES) {
			t = in.nextInt();
		}
		for (int i=1; i<=t; i++) {
			solve(i);
		}
		out.flush();
	}

	// ---------------------------------------------------------------------------------------------- //

	void go() throws Exception {

		if (LOCAL && USE_FILE == 0) {
			//  needs to be set locally or expects input from terminal
			System.setIn(new ByteArrayInputStream(INPUT.getBytes()));
			in = new Scanner(System.in);
		}
		if (LOCAL && USE_FILE > 0) {
			String filename = String.format("in/cf%d.txt", USE_FILE);
			File inputFile = new File(filename);
			in = new Scanner(inputFile);
			out.printf("[%s]\n", filename);
			out.flush();
		}
		if (!LOCAL) {
			in = new Scanner(System.in);
		}

		long startTime = System.currentTimeMillis();
		testCases();
		if (LOCAL) {
			System.out.printf("[%dms]\n", System.currentTimeMillis()-startTime);
		}
		in.close();
	}

	static boolean LOCAL = System.getProperty("ONLINE_JUDGE") == null;
	Scanner in;
	PrintWriter out = new PrintWriter(System.out);

}


import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;

public class D_4 {
	public static void main(String[] args) throws Exception {
		new D_4().go();
	}

	int USE_FILE = 1;
	String INPUT = "4\r\n" +
			"4 3 2 1 2\r\n" +
			"1 2\r\n" +
			"1 3\r\n" +
			"1 4\r\n" +
			"6 6 1 2 5\r\n" +
			"1 2\r\n" +
			"6 5\r\n" +
			"2 3\r\n" +
			"3 4\r\n" +
			"4 5\r\n" +
			"9 3 9 2 5\r\n" +
			"1 2\r\n" +
			"1 6\r\n" +
			"1 9\r\n" +
			"1 3\r\n" +
			"9 5\r\n" +
			"7 9\r\n" +
			"4 8\r\n" +
			"4 3\r\n" +
			"11 8 11 3 3\r\n" +
			"1 2\r\n" +
			"11 9\r\n" +
			"4 9\r\n" +
			"6 5\r\n" +
			"2 10\r\n" +
			"3 2\r\n" +
			"5 9\r\n" +
			"8 3\r\n" +
			"7 4\r\n" +
			"7 10";

	void solve(int caseNr) {
		int n = in.nextInt();
		int a = in.nextInt();
		int b = in.nextInt();
		int da = in.nextInt();
		int db = in.nextInt();

		nodes = new Node[n+1];

		for (int i = 1; i < n+1; i++) {
			nodes[i] = new Node(i);
		}

		for (int i = 1; i <= n-1; i++) {
			int n1 = in.nextInt();
			int n2 = in.nextInt();
			// System.out.printf("(%d %d) \n", n1, n2);
			nodes[n1].c.add(nodes[n2]);
			nodes[n2].c.add(nodes[n1]);
		}

		// This method will find the tree-diameter starting from any node
		findDepth(1);
		findDepth(deepest_node.id);

		int tree_diameter = max_distance;

		findDistance(a,b);
		// System.out.println(ab_distance);

		if (ab_distance <= da) {
			out.println("Alice");
			return;
		}
		if (2*da >= tree_diameter) {
			out.println("Alice");
			return;
		}
		if (db <= 2*da) {
			out.println("Alice");
			return;
		}
		out.println("Bob");

		return;
	} // end of solve2

	// these are unchanged
	Node[] nodes = null;

	// visit must be reset for dfs and bfs traversals
	boolean[] visited = null;

	// these are set when doing getDepth(..)
	Node deepest_node;
	int max_distance;

	// these are set when searching for the distance to a target node
	int ab_distance;
	int target_node;
	boolean search_done = false;

	void findDistance(int n1, int n2) {
		int n = nodes.length;
		visited = new boolean[n+1];
		ab_distance = 0;
		target_node = n2;
		search_done = false;
		distance(nodes[n1], 0);
	}

	void distance(Node n, int depth) {
		if (search_done) return;
		visited[n.id] = true;

		if (n.id == target_node) {
			ab_distance = depth;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			distance(nod, depth+1);
		}
	}

	// gets depth and assigns deepest_node
	void findDepth(int node_id) {
		int n = nodes.length;
		visited = new boolean[n+1];
		deepest_node = nodes[node_id];
		depth(nodes[node_id], 0);
	}

	void depth(Node n, int depth) {
		visited[n.id] = true;

		// System.out.println(depth);
		// System.out.println("n.id = "+n.id);

		if (depth > max_distance) {
			max_distance = depth;
			deepest_node = n;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			depth(nod, depth+1);
		}
	}

	class Node {
		int id;
		List<Node> c = new ArrayList<>();

		public Node(int id) {
			this.id = id;
		}
	}

	// ---------------------------------------------------------------------------------------------- //

	boolean HAS_TESTCASES = true;
	void testCases() {
		int t = 1;
		if (HAS_TESTCASES) {
			t = in.nextInt();
		}
		for (int i=1; i<=t; i++) {
			solve(i);
		}
		out.flush();
	}

	// ---------------------------------------------------------------------------------------------- //

	void go() throws Exception {

		if (LOCAL && USE_FILE == 0) {
			//  needs to be set locally or expects input from terminal
			System.setIn(new ByteArrayInputStream(INPUT.getBytes()));
			in = new Scanner(System.in);
		}
		if (LOCAL && USE_FILE > 0) {
			String filename = String.format("in/cf%d.txt", USE_FILE);
			File inputFile = new File(filename);
			in = new Scanner(inputFile);
			out.printf("[%s]\n", filename);
			out.flush();
		}
		if (!LOCAL) {
			in = new Scanner(System.in);
		}

		long startTime = System.currentTimeMillis();
		testCases();
		if (LOCAL) {
			System.out.printf("[%dms]\n", System.currentTimeMillis()-startTime);
		}
		in.close();
	}

	static boolean LOCAL = System.getProperty("ONLINE_JUDGE") == null;
	Scanner in;
	PrintWriter out = new PrintWriter(System.out);

}


import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Scanner;

public class D_4 {
	public static void main(String[] args) throws Exception {
		new D_4().go();
	}

	int USE_FILE = 0;
	String INPUT = "4\r\n" +
			"4 3 2 1 2\r\n" +
			"1 2\r\n" +
			"1 3\r\n" +
			"1 4\r\n" +
			"6 6 1 2 5\r\n" +
			"1 2\r\n" +
			"6 5\r\n" +
			"2 3\r\n" +
			"3 4\r\n" +
			"4 5\r\n" +
			"9 3 9 2 5\r\n" +
			"1 2\r\n" +
			"1 6\r\n" +
			"1 9\r\n" +
			"1 3\r\n" +
			"9 5\r\n" +
			"7 9\r\n" +
			"4 8\r\n" +
			"4 3\r\n" +
			"11 8 11 3 3\r\n" +
			"1 2\r\n" +
			"11 9\r\n" +
			"4 9\r\n" +
			"6 5\r\n" +
			"2 10\r\n" +
			"3 2\r\n" +
			"5 9\r\n" +
			"8 3\r\n" +
			"7 4\r\n" +
			"7 10";

	boolean test2 = false;

	void solve(int caseNr) {
		int n = in.nextInt();
		int a = in.nextInt();
		int b = in.nextInt();
		int da = in.nextInt();
		int db = in.nextInt();

		nodes = new Node[n+1];

		for (int i = 1; i < n+1; i++) {
			nodes[i] = new Node(i);
		}

		String[] input_data = new String[n];

		for (int i = 1; i <= n-1; i++) {

			int n1 = in.nextInt();
			int n2 = in.nextInt();
			input_data[i] = String.format("%d %d", n1, n2);

			// System.out.printf("(%d %d) \n", n1, n2);
			nodes[n1].c.add(nodes[n2]);
			nodes[n2].c.add(nodes[n1]);
		}

		// This method will find the tree-diameter starting from any node
		findDepth(1);
		findDepth(deepest_node.id);

		int tree_diameter = max_distance;

		findDistance(a,b);
		// System.out.println(ab_distance);

		//		for (int i = 1; i <= n; i++) {
		//			findDepth(i);
		//			findDepth(deepest_node.id);
		//			System.out.println(max_distance);
		//		}
		//		for (int i = 1; i <= n; i++) {
		//			findDistance(7,i);
		//			System.out.printf("distance from 8 to %2d = %4d\n", i, ab_distance);
		//		}

		if (!test2) {
			if (ab_distance <= da) {
				out.println("Alice");
				return;
			}
			if (2*da >= tree_diameter) {
				out.println("Alice");
				return;
			}
			if (db <= 2*da) {
				out.println("Alice");
				return;
			}
			out.println("Bob");
			return;
		}

		if (caseNr == 105) {
			out.printf("Data for testcase %d", caseNr);

			// if (caseNr == 2) {
			for (String s : input_data) {
				out.println(s);
			}

			out.printf("n=%d a=%d b=%d da=%d db=%d \n", n, a, b, da, db);
			for (int i = 1; i <= n; i++) {
				nodes[i].sortChildren();
				out.println(nodes[i]);
			}
		}

		return;
	} // end of solve2

	// these are unchanged
	Node[] nodes = null;

	// visit must be reset for dfs and bfs traversals
	boolean[] visited = null;

	// these are set when doing getDepth(..)
	Node deepest_node;
	int max_distance;

	// these are set when searching for the distance to a target node
	int ab_distance;
	int target_node;
	boolean search_done = false;

	void findDistance(int n1, int n2) {
		int n = nodes.length;
		visited = new boolean[n+1];
		ab_distance = 0;
		target_node = n2;
		search_done = false;
		distance(nodes[n1], 0);
	}

	void distance(Node n, int depth) {
		if (search_done) return;
		visited[n.id] = true;

		if (n.id == target_node) {
			ab_distance = depth;
			search_done = true;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			distance(nod, depth+1);
		}
	}

	// gets depth and assigns deepest_node
	void findDepth(int node_id) {
		int n = nodes.length;
		visited = new boolean[n+1];
		deepest_node = nodes[node_id];
		depth(nodes[node_id], 0);
	}

	void depth(Node n, int depth) {
		visited[n.id] = true;

		// System.out.println(depth);
		// System.out.println("n.id = "+n.id);

		if (depth > max_distance) {
			max_distance = depth;
			deepest_node = n;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			depth(nod, depth+1);
		}
	}

	class Node implements Comparable<Node> {
		int id;
		List<Node> c = new ArrayList<>();

		public Node(int id) {
			this.id = id;
		}

		@Override
		public String toString() {
			String str_rtn = "";
			for (Node n : c) {
				str_rtn += String.format("%d > %d    ", id, n.id);
			}
			return str_rtn;
		}

		public void sortChildren() {
			Collections.sort(c);
		}

		@Override
		public int compareTo(Node n2) {
			return this.id - n2.id;
		}
	}

	// ---------------------------------------------------------------------------------------------- //

	boolean HAS_TESTCASES = true;
	void testCases() {
		int t = 1;
		if (HAS_TESTCASES) {
			t = in.nextInt();
		}

		if (t == 10000) {
			test2 = true;
		}

		for (int i=1; i<=t; i++) {
			solve(i);
		}
		out.flush();
	}

	// ---------------------------------------------------------------------------------------------- //

	void go() throws Exception {

		if (LOCAL && USE_FILE == 0) {
			//  needs to be set locally or expects input from terminal
			System.setIn(new ByteArrayInputStream(INPUT.getBytes()));
			in = new Scanner(System.in);
		}
		if (LOCAL && USE_FILE > 0) {
			String filename = String.format("in/cf%d.txt", USE_FILE);
			File inputFile = new File(filename);
			in = new Scanner(inputFile);
			out.printf("[%s]\n", filename);
			out.flush();
		}
		if (!LOCAL) {
			in = new Scanner(System.in);
		}

		long startTime = System.currentTimeMillis();
		testCases();
		if (LOCAL) {
			System.out.printf("[%dms]\n", System.currentTimeMillis()-startTime);
		}
		in.close();
	}

	static boolean LOCAL = System.getProperty("ONLINE_JUDGE") == null;
	Scanner in;
	PrintWriter out = new PrintWriter(System.out);

}


import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;
import static java.lang.Math.*;

public class D {
	public static void main(String[] args) throws Exception {
		new D().go();
	}

	int USE_FILE = 0;
	String INPUT = "4\r\n" +
			"4 3 2 1 2\r\n" +
			"1 2\r\n" +
			"1 3\r\n" +
			"1 4\r\n" +
			"6 6 1 2 5\r\n" +
			"1 2\r\n" +
			"6 5\r\n" +
			"2 3\r\n" +
			"3 4\r\n" +
			"4 5\r\n" +
			"9 3 9 2 5\r\n" +
			"1 2\r\n" +
			"1 6\r\n" +
			"1 9\r\n" +
			"1 3\r\n" +
			"9 5\r\n" +
			"7 9\r\n" +
			"4 8\r\n" +
			"4 3\r\n" +
			"11 8 11 3 3\r\n" +
			"1 2\r\n" +
			"11 9\r\n" +
			"4 9\r\n" +
			"6 5\r\n" +
			"2 10\r\n" +
			"3 2\r\n" +
			"5 9\r\n" +
			"8 3\r\n" +
			"7 4\r\n" +
			"7 10";

	void solve(int caseNr) {
		int n = in.nextInt();
		int a = in.nextInt();
		int b = in.nextInt();
		int da = in.nextInt();
		int db = in.nextInt();

		Node[] nodes = new Node[n+1];

		for (int i = 1; i < n+1; i++) {
			nodes[i] = new Node(i);
		}

		for (int i = 1; i <= n-1; i++) {
			int n1 = in.nextInt();
			int n2 = in.nextInt();
			// System.out.printf("(%d %d) \n", n1, n2);
			nodes[n1].c.add(nodes[n2]);
			nodes[n2].c.add(nodes[n1]);
		}

		//		if (caseNr != 1) return;
		// System.out.println(nodes.length);

		visited = new boolean[n+1];
		// showTree(nodes[1]);

		b_node = b;
		traverse(nodes[a]);
		int longest_path = largest[0] + largest[1];

		// System.out.println("ab distance = "+ab_distance);
		// System.out.println("longest path = "+longest_path);

		if (ab_distance <= da) {
			out.println("alice");
			return;
		}

		if (2*da > db-1) {
			out.println("alice");
			return;
		}

		if (longest_path < 2*da+1) {
			out.println("Alice");
			return;
		}

		out.println("Bob");

		return;
	} // end of solve2

	class Node {
		int id;
		List<Node> c = new ArrayList<>();

		public Node(int id) {
			this.id = id;
		}
	}

	int ab_distance = 0;
	int b_node;
	int depth = -1;
	int[] largest = new int[2];

	void traverse(Node n) {
		if (visited[n.id]) return;
		visited[n.id] = true;

		depth++;
		if (n.id == b_node) {
			ab_distance = depth;
			// System.out.println(depth);
		}

		if (depth > largest[0]) {
			if (depth > largest[1]) {
				largest[0] = largest[1];
				largest[0] = depth;
			} else {
				largest[0] = depth;
			}
		}

		for (Node nod :n.c) {
			traverse(nod);
		}
		depth--;

	}

	boolean[] visited;

	void showTree(Node n) {
		if (visited[n.id]) return;
		visited[n.id] = true;

		for (Node nod :n.c) {
			if (!visited[nod.id]) System.out.printf("%d -> %d \n", n.id, nod.id);
		}

		for (Node nod :n.c) {
			showTree(nod);
		}
	}

	// ---------------------------------------------------------------------------------------------- //

	boolean HAS_TESTCASES = true;
	//	boolean HAS_TESTCASES = false;

	void testCases() {
		int t = 1;
		if (HAS_TESTCASES) {
			t = in.nextInt();
		}
		for (int i=1; i<=t; i++) {
			solve(i);
		}
		out.flush();
	}

	// ---------------------------------------------------------------------------------------------- //

	void go() throws Exception {

		if (LOCAL && USE_FILE == 0) {
			//  needs to be set locally or expects input from terminal
			System.setIn(new ByteArrayInputStream(INPUT.getBytes()));
			in = new Scanner(System.in);
		}
		if (LOCAL && USE_FILE > 0) {
			String filename = String.format("in/cf%d.txt", USE_FILE);
			File inputFile = new File(filename);
			in = new Scanner(inputFile);
			out.printf("[%s]\n", filename);
			out.flush();
		}
		if (!LOCAL) {
			in = new Scanner(System.in);
		}

		long startTime = System.currentTimeMillis();
		testCases();
		if (LOCAL) {
			System.out.printf("[%dms]\n", System.currentTimeMillis()-startTime);
		}
		in.close();
	}

	static boolean LOCAL = System.getProperty("ONLINE_JUDGE") == null;
	Scanner in;
	PrintWriter out = new PrintWriter(System.out);
	private int inf = Integer.MAX_VALUE;

}


import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;

public class D_4 {
	public static void main(String[] args) throws Exception {
		new D_4().go();
	}

	int USE_FILE = 3;
	String INPUT = "4\r\n" +
			"4 3 2 1 2\r\n" +
			"1 2\r\n" +
			"1 3\r\n" +
			"1 4\r\n" +
			"6 6 1 2 5\r\n" +
			"1 2\r\n" +
			"6 5\r\n" +
			"2 3\r\n" +
			"3 4\r\n" +
			"4 5\r\n" +
			"9 3 9 2 5\r\n" +
			"1 2\r\n" +
			"1 6\r\n" +
			"1 9\r\n" +
			"1 3\r\n" +
			"9 5\r\n" +
			"7 9\r\n" +
			"4 8\r\n" +
			"4 3\r\n" +
			"11 8 11 3 3\r\n" +
			"1 2\r\n" +
			"11 9\r\n" +
			"4 9\r\n" +
			"6 5\r\n" +
			"2 10\r\n" +
			"3 2\r\n" +
			"5 9\r\n" +
			"8 3\r\n" +
			"7 4\r\n" +
			"7 10";

	boolean test2 = false;

	void solve(int caseNr) {
		int n = in.nextInt();
		int a = in.nextInt();
		int b = in.nextInt();
		int da = in.nextInt();
		int db = in.nextInt();

		nodes = new Node[n+1];

		for (int i = 1; i < n+1; i++) {
			nodes[i] = new Node(i);
		}

		String[] input_data = new String[n];

		for (int i = 1; i <= n-1; i++) {

			int n1 = in.nextInt();
			int n2 = in.nextInt();
			input_data[i] = String.format("%d %d", n1, n2);

			// System.out.printf("(%d %d) \n", n1, n2);
			nodes[n1].c.add(nodes[n2]);
			nodes[n2].c.add(nodes[n1]);
		}

		// This method will find the tree-diameter starting from any node
		findDepth(1);
		findDepth(deepest_node.id);

		int tree_diameter = max_distance;

		findDistance(a,b);
		// System.out.println(ab_distance);

		//		for (int i = 1; i <= n; i++) {
		//			findDepth(i);
		//			findDepth(deepest_node.id);
		//			System.out.println(max_distance);
		//		}
		//		for (int i = 1; i <= n; i++) {
		//			findDistance(7,i);
		//			System.out.printf("distance from 8 to %2d = %4d\n", i, ab_distance);
		//		}

		if (!test2) {
			if (ab_distance <= da) {
				out.println("Alice");
				return;
			}
			if (2*da >= tree_diameter) {
				out.println("Alice");
				return;
			}
			if (db <= 2*da) {
				out.println("Alice");
				return;
			}
			out.println("Bob");
			return;
		}

		if (caseNr == 106) {
			for (String s : input_data) {
				out.println(s);
			}

			out.printf("n=%d a=%d b=%d da=%d db=%d \n", n, a, b, da, db);
			for (int i = 1; i <= n; i++) {
				out.println(nodes[i]);
			}
		}

		return;
	} // end of solve2

	// these are unchanged
	Node[] nodes = null;

	// visit must be reset for dfs and bfs traversals
	boolean[] visited = null;

	// these are set when doing getDepth(..)
	Node deepest_node;
	int max_distance;

	// these are set when searching for the distance to a target node
	int ab_distance;
	int target_node;
	boolean search_done = false;

	void findDistance(int n1, int n2) {
		int n = nodes.length;
		visited = new boolean[n+1];
		ab_distance = 0;
		target_node = n2;
		search_done = false;
		distance(nodes[n1], 0);
	}

	void distance(Node n, int depth) {
		if (search_done) return;
		visited[n.id] = true;

		if (n.id == target_node) {
			ab_distance = depth;
			search_done = true;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			distance(nod, depth+1);
		}
	}

	// gets depth and assigns deepest_node
	void findDepth(int node_id) {
		int n = nodes.length;
		visited = new boolean[n+1];
		deepest_node = nodes[node_id];
		depth(nodes[node_id], 0);
	}

	void depth(Node n, int depth) {
		visited[n.id] = true;

		// System.out.println(depth);
		// System.out.println("n.id = "+n.id);

		if (depth > max_distance) {
			max_distance = depth;
			deepest_node = n;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			depth(nod, depth+1);
		}
	}

	class Node {
		int id;
		List<Node> c = new ArrayList<>();

		public Node(int id) {
			this.id = id;
		}

		@Override
		public String toString() {
			String str_rtn = "";
			for (Node n : c) {
				str_rtn += String.format("%d > %d    ", id, n.id);
			}
			return str_rtn;
		}
	}

	// ---------------------------------------------------------------------------------------------- //

	boolean HAS_TESTCASES = true;
	void testCases() {
		int t = 1;
		if (HAS_TESTCASES) {
			t = in.nextInt();
		}

		if (t == 10000) {
			test2 = true;
		}

		for (int i=1; i<=t; i++) {
			solve(i);
		}
		out.flush();
	}

	// ---------------------------------------------------------------------------------------------- //

	void go() throws Exception {

		if (LOCAL && USE_FILE == 0) {
			//  needs to be set locally or expects input from terminal
			System.setIn(new ByteArrayInputStream(INPUT.getBytes()));
			in = new Scanner(System.in);
		}
		if (LOCAL && USE_FILE > 0) {
			String filename = String.format("in/cf%d.txt", USE_FILE);
			File inputFile = new File(filename);
			in = new Scanner(inputFile);
			out.printf("[%s]\n", filename);
			out.flush();
		}
		if (!LOCAL) {
			in = new Scanner(System.in);
		}

		long startTime = System.currentTimeMillis();
		testCases();
		if (LOCAL) {
			System.out.printf("[%dms]\n", System.currentTimeMillis()-startTime);
		}
		in.close();
	}

	static boolean LOCAL = System.getProperty("ONLINE_JUDGE") == null;
	Scanner in;
	PrintWriter out = new PrintWriter(System.out);

}


import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;
import static java.lang.Math.*;

public class D_2 {
	public static void main(String[] args) throws Exception {
		new D_2().go();
	}

	int USE_FILE = 0;
	String INPUT = "4\r\n" +
			"4 3 2 1 2\r\n" +
			"1 2\r\n" +
			"1 3\r\n" +
			"1 4\r\n" +
			"6 6 1 2 5\r\n" +
			"1 2\r\n" +
			"6 5\r\n" +
			"2 3\r\n" +
			"3 4\r\n" +
			"4 5\r\n" +
			"9 3 9 2 5\r\n" +
			"1 2\r\n" +
			"1 6\r\n" +
			"1 9\r\n" +
			"1 3\r\n" +
			"9 5\r\n" +
			"7 9\r\n" +
			"4 8\r\n" +
			"4 3\r\n" +
			"11 8 11 3 3\r\n" +
			"1 2\r\n" +
			"11 9\r\n" +
			"4 9\r\n" +
			"6 5\r\n" +
			"2 10\r\n" +
			"3 2\r\n" +
			"5 9\r\n" +
			"8 3\r\n" +
			"7 4\r\n" +
			"7 10";

	void solve(int caseNr) {
		int n = in.nextInt();
		int a = in.nextInt();
		int b = in.nextInt();
		int da = in.nextInt();
		int db = in.nextInt();

		Node[] nodes = new Node[n+1];

		for (int i = 1; i < n+1; i++) {
			nodes[i] = new Node(i);
		}

		for (int i = 1; i <= n-1; i++) {
			int n1 = in.nextInt();
			int n2 = in.nextInt();
			// System.out.printf("(%d %d) \n", n1, n2);
			nodes[n1].c.add(nodes[n2]);
			nodes[n2].c.add(nodes[n1]);
		}

		//		if (caseNr != 4) return;
		// System.out.println(nodes.length);

		visited = new boolean[n+1];
		b_node = b;
		get_ab_distance(nodes[a]);

		visited = new boolean[n+1];
		visited[1] = true;
		int[] largest = new int[2];
		for (Node nod : nodes[1].c) {
			int depth = depth(nod, 1);

			if (depth > largest[0]) {
				if (depth > largest[1]) {
					largest[0] = largest[1];
					largest[1] = depth;
				} else {
					largest[0] = depth;
				}
			}

		}

		int tree_width = largest[0] + largest[1];

		// System.out.println(tree_width);

		// System.out.println("ab distance = "+ab_distance);
		// System.out.println("longest path = "+longest_path);

		if (ab_distance <= da) {
			out.println("Alice");
			return;
		}
		if (2*da >= tree_width) {
			out.println("Alice");
			return;
		}
		if (db <= 2*da) {
			out.println("Alice");
			return;
		}

		//		if (ab_distance <= da) {
		//			out.println("Alice");
		//			return;
		//		}
		//		if (2*da > db-1) {
		//			out.println("Alice");
		//			return;
		//		}
		//		if (tree_width < 2*da+1) {
		//			out.println("Alice");
		//			return;
		//		}
		//		out.println("Bob");

		return;
	} // end of solve2

	class Node {
		int id;
		List<Node> c = new ArrayList<>();

		public Node(int id) {
			this.id = id;
		}
	}

	int depth(Node n, int depth) {
		visited[n.id] = true;

		int max_depth = depth;
		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			max_depth = max(max_depth, depth(nod, depth+1));
		}

		return max_depth;
	}

	int ab_distance = 0;
	int b_node;
	int depth = -1;
	int[] largest = new int[2];

	void get_ab_distance(Node n) {
		if (visited[n.id]) return;
		visited[n.id] = true;

		depth++;
		if (n.id == b_node) {
			ab_distance = depth;
			// System.out.println(depth);
		}

		for (Node nod :n.c) {
			get_ab_distance(nod);
		}
		depth--;
	}

	boolean[] visited;

	void showTree(Node n) {
		if (visited[n.id]) return;
		visited[n.id] = true;

		for (Node nod :n.c) {
			if (!visited[nod.id]) System.out.printf("%d -> %d \n", n.id, nod.id);
		}

		for (Node nod :n.c) {
			showTree(nod);
		}
	}

	// ---------------------------------------------------------------------------------------------- //

	boolean HAS_TESTCASES = true;
	//	boolean HAS_TESTCASES = false;

	void testCases() {
		int t = 1;
		if (HAS_TESTCASES) {
			t = in.nextInt();
		}
		for (int i=1; i<=t; i++) {
			solve(i);
		}
		out.flush();
	}

	// ---------------------------------------------------------------------------------------------- //

	void go() throws Exception {

		if (LOCAL && USE_FILE == 0) {
			//  needs to be set locally or expects input from terminal
			System.setIn(new ByteArrayInputStream(INPUT.getBytes()));
			in = new Scanner(System.in);
		}
		if (LOCAL && USE_FILE > 0) {
			String filename = String.format("in/cf%d.txt", USE_FILE);
			File inputFile = new File(filename);
			in = new Scanner(inputFile);
			out.printf("[%s]\n", filename);
			out.flush();
		}
		if (!LOCAL) {
			in = new Scanner(System.in);
		}

		long startTime = System.currentTimeMillis();
		testCases();
		if (LOCAL) {
			System.out.printf("[%dms]\n", System.currentTimeMillis()-startTime);
		}
		in.close();
	}

	static boolean LOCAL = System.getProperty("ONLINE_JUDGE") == null;
	Scanner in;
	PrintWriter out = new PrintWriter(System.out);
	private int inf = Integer.MAX_VALUE;

}


import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;

public class D_4 {
	public static void main(String[] args) throws Exception {
		new D_4().go();
	}

	int USE_FILE = 1;
	String INPUT = "4\r\n" +
			"4 3 2 1 2\r\n" +
			"1 2\r\n" +
			"1 3\r\n" +
			"1 4\r\n" +
			"6 6 1 2 5\r\n" +
			"1 2\r\n" +
			"6 5\r\n" +
			"2 3\r\n" +
			"3 4\r\n" +
			"4 5\r\n" +
			"9 3 9 2 5\r\n" +
			"1 2\r\n" +
			"1 6\r\n" +
			"1 9\r\n" +
			"1 3\r\n" +
			"9 5\r\n" +
			"7 9\r\n" +
			"4 8\r\n" +
			"4 3\r\n" +
			"11 8 11 3 3\r\n" +
			"1 2\r\n" +
			"11 9\r\n" +
			"4 9\r\n" +
			"6 5\r\n" +
			"2 10\r\n" +
			"3 2\r\n" +
			"5 9\r\n" +
			"8 3\r\n" +
			"7 4\r\n" +
			"7 10";

	boolean test2 = false;

	void solve(int caseNr) {
		int n = in.nextInt();
		int a = in.nextInt();
		int b = in.nextInt();
		int da = in.nextInt();
		int db = in.nextInt();

		nodes = new Node[n+1];

		for (int i = 1; i < n+1; i++) {
			nodes[i] = new Node(i);
		}

		for (int i = 1; i <= n-1; i++) {
			int n1 = in.nextInt();
			int n2 = in.nextInt();
			// System.out.printf("(%d %d) \n", n1, n2);
			nodes[n1].c.add(nodes[n2]);
			nodes[n2].c.add(nodes[n1]);
		}

		// This method will find the tree-diameter starting from any node
		findDepth(1);
		findDepth(deepest_node.id);

		int tree_diameter = max_distance;

		findDistance(a,b);
		// System.out.println(ab_distance);

		//		for (int i = 1; i <= n; i++) {
		//			findDepth(i);
		//			findDepth(deepest_node.id);
		//			System.out.println(max_distance);
		//		}
		//		for (int i = 1; i <= n; i++) {
		//			findDistance(7,i);
		//			System.out.printf("distance from 8 to %2d = %4d\n", i, ab_distance);
		//		}

		if (!test2) {
			if (ab_distance <= da) {
				out.println("Alice");
				return;
			}
			if (2*da >= tree_diameter) {
				out.println("Alice");
				return;
			}
			if (db <= 2*da) {
				out.println("Alice");
				return;
			}
			out.println("Bob");
			return;
		}

		if (caseNr == 106) {
			out.printf("n=%d a=%d b=%d da=%d db=%d \n", n, a, b, da, db);
			for (int i = 1; i <= n; i++) {
				out.println(nodes[i]);
			}
		}

		return;
	} // end of solve2

	// these are unchanged
	Node[] nodes = null;

	// visit must be reset for dfs and bfs traversals
	boolean[] visited = null;

	// these are set when doing getDepth(..)
	Node deepest_node;
	int max_distance;

	// these are set when searching for the distance to a target node
	int ab_distance;
	int target_node;
	boolean search_done = false;

	void findDistance(int n1, int n2) {
		int n = nodes.length;
		visited = new boolean[n+1];
		ab_distance = 0;
		target_node = n2;
		search_done = false;
		distance(nodes[n1], 0);
	}

	void distance(Node n, int depth) {
		if (search_done) return;
		visited[n.id] = true;

		if (n.id == target_node) {
			ab_distance = depth;
			search_done = true;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			distance(nod, depth+1);
		}
	}

	// gets depth and assigns deepest_node
	void findDepth(int node_id) {
		int n = nodes.length;
		visited = new boolean[n+1];
		deepest_node = nodes[node_id];
		depth(nodes[node_id], 0);
	}

	void depth(Node n, int depth) {
		visited[n.id] = true;

		// System.out.println(depth);
		// System.out.println("n.id = "+n.id);

		if (depth > max_distance) {
			max_distance = depth;
			deepest_node = n;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			depth(nod, depth+1);
		}
	}

	class Node {
		int id;
		List<Node> c = new ArrayList<>();

		public Node(int id) {
			this.id = id;
		}

		@Override
		public String toString() {
			String str_rtn = "";
			for (Node n : c) {
				str_rtn += String.format("%d > %d    ", id, n.id);
			}
			return str_rtn;
		}
	}

	// ---------------------------------------------------------------------------------------------- //

	boolean HAS_TESTCASES = true;
	void testCases() {
		int t = 1;
		if (HAS_TESTCASES) {
			t = in.nextInt();
		}

		if (t == 10000) {
			test2 = true;
		}

		for (int i=1; i<=t; i++) {
			solve(i);
		}
		out.flush();
	}

	// ---------------------------------------------------------------------------------------------- //

	void go() throws Exception {

		if (LOCAL && USE_FILE == 0) {
			//  needs to be set locally or expects input from terminal
			System.setIn(new ByteArrayInputStream(INPUT.getBytes()));
			in = new Scanner(System.in);
		}
		if (LOCAL && USE_FILE > 0) {
			String filename = String.format("in/cf%d.txt", USE_FILE);
			File inputFile = new File(filename);
			in = new Scanner(inputFile);
			out.printf("[%s]\n", filename);
			out.flush();
		}
		if (!LOCAL) {
			in = new Scanner(System.in);
		}

		long startTime = System.currentTimeMillis();
		testCases();
		if (LOCAL) {
			System.out.printf("[%dms]\n", System.currentTimeMillis()-startTime);
		}
		in.close();
	}

	static boolean LOCAL = System.getProperty("ONLINE_JUDGE") == null;
	Scanner in;
	PrintWriter out = new PrintWriter(System.out);

}


import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Scanner;

public class D_5 {
	public static void main(String[] args) throws Exception {
		new D_5().go();
	}

	int USE_FILE = 3;
	String INPUT = "4\r\n" +
			"4 3 2 1 2\r\n" +
			"1 2\r\n" +
			"1 3\r\n" +
			"1 4\r\n" +
			"6 6 1 2 5\r\n" +
			"1 2\r\n" +
			"6 5\r\n" +
			"2 3\r\n" +
			"3 4\r\n" +
			"4 5\r\n" +
			"9 3 9 2 5\r\n" +
			"1 2\r\n" +
			"1 6\r\n" +
			"1 9\r\n" +
			"1 3\r\n" +
			"9 5\r\n" +
			"7 9\r\n" +
			"4 8\r\n" +
			"4 3\r\n" +
			"11 8 11 3 3\r\n" +
			"1 2\r\n" +
			"11 9\r\n" +
			"4 9\r\n" +
			"6 5\r\n" +
			"2 10\r\n" +
			"3 2\r\n" +
			"5 9\r\n" +
			"8 3\r\n" +
			"7 4\r\n" +
			"7 10";

	void solve(int caseNr) {
		int n = in.nextInt();
		int a = in.nextInt();
		int b = in.nextInt();
		int da = in.nextInt();
		int db = in.nextInt();

		nodes = new Node[n+1];

		for (int i = 1; i < n+1; i++) {
			nodes[i] = new Node(i);
		}

		for (int i = 1; i <= n-1; i++) {
			int n1 = in.nextInt();
			int n2 = in.nextInt();
			// System.out.printf("(%d %d) \n", n1, n2);
			nodes[n1].c.add(nodes[n2]);
			nodes[n2].c.add(nodes[n1]);
		}

		// This method will find the tree-diameter starting from any node
		findDepth(1);
		findDepth(deepest_node.id);

		int tree_diameter = max_distance;

		findDistance(a,b);
		// System.out.println(ab_distance);

		//		for (int i = 1; i <= n; i++) {
		//			findDepth(i);
		//			findDepth(deepest_node.id);
		//			System.out.println(max_distance);
		//		}
		//		for (int i = 1; i <= n; i++) {
		//			findDistance(7,i);
		//			System.out.printf("distance from 8 to %2d = %4d\n", i, ab_distance);
		//		}

		//		out.printf("n=%d a=%d b=%d da=%d db=%d \n", n, a, b, da, db);
		//		for (int i = 1; i <= n; i++) {
		//			nodes[i].sortChildren();
		//			out.println(nodes[i]);
		//		}

		if (ab_distance <= da) {
			out.println("Alice");
			return;
		}
		if (2*da >= tree_diameter) {
			out.println("Alice");
			return;
		}
		if (db <= 2*da) {
			out.println("Alice");
			return;
		}
		out.println("Bob");

		return;
	} // end of solve2

	// these are unchanged
	Node[] nodes = null;

	// visit must be reset for dfs and bfs traversals
	boolean[] visited = null;

	// these are set when doing getDepth(..)
	Node deepest_node;
	int max_distance;

	// these are set when searching for the distance to a target node
	int ab_distance;
	int target_node;
	boolean search_done = false;

	void findDistance(int n1, int n2) {
		int n = nodes.length;
		visited = new boolean[n+1];
		ab_distance = 0;
		target_node = n2;
		search_done = false;
		distance(nodes[n1], 0);
	}

	void distance(Node n, int depth) {
		if (search_done) return;
		visited[n.id] = true;

		if (n.id == target_node) {
			ab_distance = depth;
			search_done = true;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			distance(nod, depth+1);
		}
	}

	// gets depth and assigns deepest_node
	void findDepth(int node_id) {
		int n = nodes.length;
		visited = new boolean[n+1];
		deepest_node = nodes[node_id];
		depth(nodes[node_id], 0);
	}

	void depth(Node n, int depth) {
		visited[n.id] = true;

		// System.out.println(depth);
		// System.out.println("n.id = "+n.id);

		if (depth > max_distance) {
			max_distance = depth;
			deepest_node = n;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			depth(nod, depth+1);
		}
	}

	class Node implements Comparable<Node> {
		int id;
		List<Node> c = new ArrayList<>();

		public Node(int id) {
			this.id = id;
		}

		@Override
		public String toString() {
			String str_rtn = "";
			for (Node n : c) {
				str_rtn += String.format("%d > %d    ", id, n.id);
			}
			return str_rtn;
		}

		public void sortChildren() {
			Collections.sort(c);
		}

		@Override
		public int compareTo(Node n2) {
			return this.id - n2.id;
		}
	}

	// ---------------------------------------------------------------------------------------------- //

	boolean HAS_TESTCASES = true;
	void testCases() {
		int t = 1;
		if (HAS_TESTCASES) {
			t = in.nextInt();
		}
		for (int i=1; i<=t; i++) {
			solve(i);
		}
		out.flush();
	}

	// ---------------------------------------------------------------------------------------------- //

	void go() throws Exception {

		if (LOCAL && USE_FILE == 0) {
			//  needs to be set locally or expects input from terminal
			System.setIn(new ByteArrayInputStream(INPUT.getBytes()));
			in = new Scanner(System.in);
		}
		if (LOCAL && USE_FILE > 0) {
			String filename = String.format("in/cf%d.txt", USE_FILE);
			File inputFile = new File(filename);
			in = new Scanner(inputFile);
			out.printf("[%s]\n", filename);
			out.flush();
		}
		if (!LOCAL) {
			in = new Scanner(System.in);
		}

		long startTime = System.currentTimeMillis();
		testCases();
		if (LOCAL) {
			System.out.printf("[%dms]\n", System.currentTimeMillis()-startTime);
		}
		in.close();
	}

	static boolean LOCAL = System.getProperty("ONLINE_JUDGE") == null;
	Scanner in;
	PrintWriter out = new PrintWriter(System.out);

}


import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;

public class D_4 {
	public static void main(String[] args) throws Exception {
		new D_4().go();
	}

	int USE_FILE = 0;
	String INPUT = "4\r\n" +
			"4 3 2 1 2\r\n" +
			"1 2\r\n" +
			"1 3\r\n" +
			"1 4\r\n" +
			"6 6 1 2 5\r\n" +
			"1 2\r\n" +
			"6 5\r\n" +
			"2 3\r\n" +
			"3 4\r\n" +
			"4 5\r\n" +
			"9 3 9 2 5\r\n" +
			"1 2\r\n" +
			"1 6\r\n" +
			"1 9\r\n" +
			"1 3\r\n" +
			"9 5\r\n" +
			"7 9\r\n" +
			"4 8\r\n" +
			"4 3\r\n" +
			"11 8 11 3 3\r\n" +
			"1 2\r\n" +
			"11 9\r\n" +
			"4 9\r\n" +
			"6 5\r\n" +
			"2 10\r\n" +
			"3 2\r\n" +
			"5 9\r\n" +
			"8 3\r\n" +
			"7 4\r\n" +
			"7 10";

	void solve(int caseNr) {
		int n = in.nextInt();
		int a = in.nextInt();
		int b = in.nextInt();
		int da = in.nextInt();
		int db = in.nextInt();

		nodes = new Node[n+1];

		for (int i = 1; i < n+1; i++) {
			nodes[i] = new Node(i);
		}

		for (int i = 1; i <= n-1; i++) {
			int n1 = in.nextInt();
			int n2 = in.nextInt();
			// System.out.printf("(%d %d) \n", n1, n2);
			nodes[n1].c.add(nodes[n2]);
			nodes[n2].c.add(nodes[n1]);
		}

		// This method will find the tree-diameter starting from any node
		findDepth(1);
		findDepth(deepest_node.id);
		findDistance(a,b);

		if (ab_distance <= da) {
			out.println("Alice");
			return;
		}
		if (2*da > db-1) {
			out.println("Alice");
			return;
		}
		if (max_distance < 2*da+1) {
			out.println("Alice");
			return;
		}

		out.println("Bob");

		return;
	} // end of solve2

	// these are unchanged
	Node[] nodes = null;

	// visit must be reset for dfs and bfs traversals
	boolean[] visited = null;

	// these are set when doing getDepth(..)
	Node deepest_node;
	int max_distance;

	// these are set when searching for the distance to a target node
	int ab_distance;
	int target_node;
	boolean search_done = false;

	void findDistance(int n1, int n2) {
		int n = nodes.length;
		visited = new boolean[n+1];
		ab_distance = 0;
		target_node = n2;
		search_done = false;
		distance(nodes[n1], 0);
	}

	void distance(Node n, int depth) {
		if (search_done) return;
		visited[n.id] = true;

		if (n.id == target_node) {
			ab_distance = depth;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			distance(nod, depth+1);
		}
	}

	// gets depth and assigns deepest_node
	void findDepth(int node_id) {
		int n = nodes.length;
		visited = new boolean[n+1];
		deepest_node = nodes[node_id];
		depth(nodes[node_id], 0);
	}

	void depth(Node n, int depth) {
		visited[n.id] = true;

		// System.out.println(depth);
		// System.out.println("n.id = "+n.id);

		if (depth > max_distance) {
			max_distance = depth;
			deepest_node = n;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			depth(nod, depth+1);
		}
	}

	class Node {
		int id;
		List<Node> c = new ArrayList<>();

		public Node(int id) {
			this.id = id;
		}
	}

	// ---------------------------------------------------------------------------------------------- //

	boolean HAS_TESTCASES = true;
	void testCases() {
		int t = 1;
		if (HAS_TESTCASES) {
			t = in.nextInt();
		}
		for (int i=1; i<=t; i++) {
			solve(i);
		}
		out.flush();
	}

	// ---------------------------------------------------------------------------------------------- //

	void go() throws Exception {

		if (LOCAL && USE_FILE == 0) {
			//  needs to be set locally or expects input from terminal
			System.setIn(new ByteArrayInputStream(INPUT.getBytes()));
			in = new Scanner(System.in);
		}
		if (LOCAL && USE_FILE > 0) {
			String filename = String.format("in/cf%d.txt", USE_FILE);
			File inputFile = new File(filename);
			in = new Scanner(inputFile);
			out.printf("[%s]\n", filename);
			out.flush();
		}
		if (!LOCAL) {
			in = new Scanner(System.in);
		}

		long startTime = System.currentTimeMillis();
		testCases();
		if (LOCAL) {
			System.out.printf("[%dms]\n", System.currentTimeMillis()-startTime);
		}
		in.close();
	}

	static boolean LOCAL = System.getProperty("ONLINE_JUDGE") == null;
	Scanner in;
	PrintWriter out = new PrintWriter(System.out);

}


import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Scanner;

public class D_5 {
	public static void main(String[] args) throws Exception {
		new D_5().go();
	}

	int USE_FILE = 6;
	String INPUT = "4\r\n" +
			"4 3 2 1 2\r\n" +
			"1 2\r\n" +
			"1 3\r\n" +
			"1 4\r\n" +
			"6 6 1 2 5\r\n" +
			"1 2\r\n" +
			"6 5\r\n" +
			"2 3\r\n" +
			"3 4\r\n" +
			"4 5\r\n" +
			"9 3 9 2 5\r\n" +
			"1 2\r\n" +
			"1 6\r\n" +
			"1 9\r\n" +
			"1 3\r\n" +
			"9 5\r\n" +
			"7 9\r\n" +
			"4 8\r\n" +
			"4 3\r\n" +
			"11 8 11 3 3\r\n" +
			"1 2\r\n" +
			"11 9\r\n" +
			"4 9\r\n" +
			"6 5\r\n" +
			"2 10\r\n" +
			"3 2\r\n" +
			"5 9\r\n" +
			"8 3\r\n" +
			"7 4\r\n" +
			"7 10";

	void solve(int caseNr) {
		int n = in.nextInt();
		int a = in.nextInt();
		int b = in.nextInt();
		int da = in.nextInt();
		int db = in.nextInt();

		nodes = new Node[n+1];

		for (int i = 1; i < n+1; i++) {
			nodes[i] = new Node(i);
		}

		for (int i = 1; i <= n-1; i++) {
			int n1 = in.nextInt();
			int n2 = in.nextInt();
			// System.out.printf("(%d %d) \n", n1, n2);
			nodes[n1].c.add(nodes[n2]);
			nodes[n2].c.add(nodes[n1]);
		}

		// This method will find the tree-diameter starting from any node
		findDepth(1);
		findDepth(deepest_node.id);

		int tree_diameter = max_distance;

		findDistance(a,b);
		// System.out.println(ab_distance);

		//		for (int i = 1; i <= n; i++) {
		//			findDepth(i);
		//			findDepth(deepest_node.id);
		//			System.out.println(max_distance);
		//		}
		//		for (int i = 1; i <= n; i++) {
		//			findDistance(7,i);
		//			System.out.printf("distance from 8 to %2d = %4d\n", i, ab_distance);
		//		}

		//		out.printf("n=%d a=%d b=%d da=%d db=%d \n", n, a, b, da, db);
		//		for (int i = 1; i <= n; i++) {
		//			nodes[i].sortChildren();
		//			out.println(nodes[i]);
		//		}

		//		if (caseNr == 2 && print_wrong) {
		//			out.println("Bob");
		//			print_wrong = false;
		//			return;
		//		}

		if (ab_distance <= da) {
			out.println("Alice");
			return;
		}
		if (2*da >= tree_diameter) {
			out.println("Alice");
			return;
		}
		if (db <= 2*da) {
			out.println("Alice");
			return;
		}
		out.println("Bob");

		return;
	} // end of solve2

	// set for each testcase and otherwise unchanged
	Node[] nodes = null;

	// visited must be reset for each dfs and bfs traversals
	boolean[] visited = null;

	// these are set when doing getDepth(..)
	Node deepest_node;
	int max_distance;

	// these are set when searching for the distance to a target node
	int ab_distance;
	int target_node;
	boolean search_done;

	void findDistance(int n1, int n2) {
		int n = nodes.length;
		visited = new boolean[n+1];
		ab_distance = 0;
		target_node = n2;
		search_done = false;
		distance(nodes[n1], 0);
	}

	void distance(Node n, int depth) {
		if (search_done) return;
		visited[n.id] = true;

		if (n.id == target_node) {
			ab_distance = depth;
			search_done = true;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			distance(nod, depth+1);
		}
	}

	// gets depth and assigns deepest_node
	void findDepth(int node_id) {
		int n = nodes.length;
		visited = new boolean[n+1];
		deepest_node = nodes[node_id];
		max_distance = 0;
		depth(nodes[node_id], 0);
	}

	void depth(Node n, int depth) {
		visited[n.id] = true;

		// System.out.println(depth);
		// System.out.println("n.id = "+n.id);

		if (depth > max_distance) {
			max_distance = depth;
			deepest_node = n;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			depth(nod, depth+1);
		}
	}

	class Node implements Comparable<Node> {
		int id;
		List<Node> c = new ArrayList<>();

		public Node(int id) {
			this.id = id;
		}

		@Override
		public String toString() {
			String str_rtn = "";
			for (Node n : c) {
				str_rtn += String.format("%d > %d    ", id, n.id);
			}
			return str_rtn;
		}

		public void sortChildren() {
			Collections.sort(c);
		}

		@Override
		public int compareTo(Node n2) {
			return this.id - n2.id;
		}
	}

	// ---------------------------------------------------------------------------------------------- //

	boolean HAS_TESTCASES = true;
	void testCases() {
		int t = 1;
		if (HAS_TESTCASES) {
			t = in.nextInt();
		}
		for (int i=1; i<=t; i++) {
			solve(i);
		}
		out.flush();
	}

	// ---------------------------------------------------------------------------------------------- //

	void go() throws Exception {

		if (LOCAL && USE_FILE == 0) {
			//  needs to be set locally or expects input from terminal
			System.setIn(new ByteArrayInputStream(INPUT.getBytes()));
			in = new Scanner(System.in);
		}
		if (LOCAL && USE_FILE > 0) {
			String filename = String.format("in/cf%d.txt", USE_FILE);
			File inputFile = new File(filename);
			in = new Scanner(inputFile);
			out.printf("[%s]\n", filename);
			out.flush();
		}
		if (!LOCAL) {
			in = new Scanner(System.in);
		}

		long startTime = System.currentTimeMillis();
		testCases();
		if (LOCAL) {
			System.out.printf("[%dms]\n", System.currentTimeMillis()-startTime);
		}
		in.close();
	}

	static boolean LOCAL = System.getProperty("ONLINE_JUDGE") == null;
	Scanner in;
	PrintWriter out = new PrintWriter(System.out);

}


import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Scanner;

public class D_4 {
	public static void main(String[] args) throws Exception {
		new D_4().go();
	}

	int USE_FILE = 0;
	String INPUT = "4\r\n" +
			"4 3 2 1 2\r\n" +
			"1 2\r\n" +
			"1 3\r\n" +
			"1 4\r\n" +
			"6 6 1 2 5\r\n" +
			"1 2\r\n" +
			"6 5\r\n" +
			"2 3\r\n" +
			"3 4\r\n" +
			"4 5\r\n" +
			"9 3 9 2 5\r\n" +
			"1 2\r\n" +
			"1 6\r\n" +
			"1 9\r\n" +
			"1 3\r\n" +
			"9 5\r\n" +
			"7 9\r\n" +
			"4 8\r\n" +
			"4 3\r\n" +
			"11 8 11 3 3\r\n" +
			"1 2\r\n" +
			"11 9\r\n" +
			"4 9\r\n" +
			"6 5\r\n" +
			"2 10\r\n" +
			"3 2\r\n" +
			"5 9\r\n" +
			"8 3\r\n" +
			"7 4\r\n" +
			"7 10";

	boolean test2 = false;

	void solve(int caseNr) {
		int n = in.nextInt();
		int a = in.nextInt();
		int b = in.nextInt();
		int da = in.nextInt();
		int db = in.nextInt();

		nodes = new Node[n+1];

		for (int i = 1; i < n+1; i++) {
			nodes[i] = new Node(i);
		}

		String[] input_data = new String[n];

		for (int i = 1; i <= n-1; i++) {

			int n1 = in.nextInt();
			int n2 = in.nextInt();
			input_data[i] = String.format("%d %d", n1, n2);

			// System.out.printf("(%d %d) \n", n1, n2);
			nodes[n1].c.add(nodes[n2]);
			nodes[n2].c.add(nodes[n1]);
		}

		// This method will find the tree-diameter starting from any node
		findDepth(1);
		findDepth(deepest_node.id);

		int tree_diameter = max_distance;

		findDistance(a,b);
		// System.out.println(ab_distance);

		//		for (int i = 1; i <= n; i++) {
		//			findDepth(i);
		//			findDepth(deepest_node.id);
		//			System.out.println(max_distance);
		//		}
		//		for (int i = 1; i <= n; i++) {
		//			findDistance(7,i);
		//			System.out.printf("distance from 8 to %2d = %4d\n", i, ab_distance);
		//		}

		if (!test2) {
			if (ab_distance <= da) {
				out.println("Alice");
				return;
			}
			if (2*da >= tree_diameter) {
				out.println("Alice");
				return;
			}
			if (db <= 2*da) {
				out.println("Alice");
				return;
			}
			out.println("Bob");
			return;
		}

		if (caseNr == 106) {
			// if (caseNr == 2) {
			for (String s : input_data) {
				out.println(s);
			}

			out.printf("n=%d a=%d b=%d da=%d db=%d \n", n, a, b, da, db);
			for (int i = 1; i <= n; i++) {
				nodes[i].sortChildren();
				out.println(nodes[i]);
			}
		}

		return;
	} // end of solve2

	// these are unchanged
	Node[] nodes = null;

	// visit must be reset for dfs and bfs traversals
	boolean[] visited = null;

	// these are set when doing getDepth(..)
	Node deepest_node;
	int max_distance;

	// these are set when searching for the distance to a target node
	int ab_distance;
	int target_node;
	boolean search_done = false;

	void findDistance(int n1, int n2) {
		int n = nodes.length;
		visited = new boolean[n+1];
		ab_distance = 0;
		target_node = n2;
		search_done = false;
		distance(nodes[n1], 0);
	}

	void distance(Node n, int depth) {
		if (search_done) return;
		visited[n.id] = true;

		if (n.id == target_node) {
			ab_distance = depth;
			search_done = true;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			distance(nod, depth+1);
		}
	}

	// gets depth and assigns deepest_node
	void findDepth(int node_id) {
		int n = nodes.length;
		visited = new boolean[n+1];
		deepest_node = nodes[node_id];
		depth(nodes[node_id], 0);
	}

	void depth(Node n, int depth) {
		visited[n.id] = true;

		// System.out.println(depth);
		// System.out.println("n.id = "+n.id);

		if (depth > max_distance) {
			max_distance = depth;
			deepest_node = n;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			depth(nod, depth+1);
		}
	}

	class Node implements Comparable<Node> {
		int id;
		List<Node> c = new ArrayList<>();

		public Node(int id) {
			this.id = id;
		}

		@Override
		public String toString() {
			String str_rtn = "";
			for (Node n : c) {
				str_rtn += String.format("%d > %d    ", id, n.id);
			}
			return str_rtn;
		}

		public void sortChildren() {
			Collections.sort(c);
		}

		@Override
		public int compareTo(Node n2) {
			return this.id - n2.id;
		}
	}

	// ---------------------------------------------------------------------------------------------- //

	boolean HAS_TESTCASES = true;
	void testCases() {
		int t = 1;
		if (HAS_TESTCASES) {
			t = in.nextInt();
		}

		if (t == 10000) {
			test2 = true;
		}

		for (int i=1; i<=t; i++) {
			solve(i);
		}
		out.flush();
	}

	// ---------------------------------------------------------------------------------------------- //

	void go() throws Exception {

		if (LOCAL && USE_FILE == 0) {
			//  needs to be set locally or expects input from terminal
			System.setIn(new ByteArrayInputStream(INPUT.getBytes()));
			in = new Scanner(System.in);
		}
		if (LOCAL && USE_FILE > 0) {
			String filename = String.format("in/cf%d.txt", USE_FILE);
			File inputFile = new File(filename);
			in = new Scanner(inputFile);
			out.printf("[%s]\n", filename);
			out.flush();
		}
		if (!LOCAL) {
			in = new Scanner(System.in);
		}

		long startTime = System.currentTimeMillis();
		testCases();
		if (LOCAL) {
			System.out.printf("[%dms]\n", System.currentTimeMillis()-startTime);
		}
		in.close();
	}

	static boolean LOCAL = System.getProperty("ONLINE_JUDGE") == null;
	Scanner in;
	PrintWriter out = new PrintWriter(System.out);

}


import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;

public class D_4 {
	public static void main(String[] args) throws Exception {
		new D_4().go();
	}

	int USE_FILE = 1;
	String INPUT = "4\r\n" +
			"4 3 2 1 2\r\n" +
			"1 2\r\n" +
			"1 3\r\n" +
			"1 4\r\n" +
			"6 6 1 2 5\r\n" +
			"1 2\r\n" +
			"6 5\r\n" +
			"2 3\r\n" +
			"3 4\r\n" +
			"4 5\r\n" +
			"9 3 9 2 5\r\n" +
			"1 2\r\n" +
			"1 6\r\n" +
			"1 9\r\n" +
			"1 3\r\n" +
			"9 5\r\n" +
			"7 9\r\n" +
			"4 8\r\n" +
			"4 3\r\n" +
			"11 8 11 3 3\r\n" +
			"1 2\r\n" +
			"11 9\r\n" +
			"4 9\r\n" +
			"6 5\r\n" +
			"2 10\r\n" +
			"3 2\r\n" +
			"5 9\r\n" +
			"8 3\r\n" +
			"7 4\r\n" +
			"7 10";

	boolean test2 = true;

	void solve(int caseNr) {
		int n = in.nextInt();
		int a = in.nextInt();
		int b = in.nextInt();
		int da = in.nextInt();
		int db = in.nextInt();

		nodes = new Node[n+1];

		for (int i = 1; i < n+1; i++) {
			nodes[i] = new Node(i);
		}

		for (int i = 1; i <= n-1; i++) {
			int n1 = in.nextInt();
			int n2 = in.nextInt();
			// System.out.printf("(%d %d) \n", n1, n2);
			nodes[n1].c.add(nodes[n2]);
			nodes[n2].c.add(nodes[n1]);
		}

		// This method will find the tree-diameter starting from any node
		findDepth(1);
		findDepth(deepest_node.id);

		int tree_diameter = max_distance;

		findDistance(a,b);
		// System.out.println(ab_distance);

		//		for (int i = 1; i <= n; i++) {
		//			findDepth(i);
		//			findDepth(deepest_node.id);
		//			System.out.println(max_distance);
		//		}
		//		for (int i = 1; i <= n; i++) {
		//			findDistance(7,i);
		//			System.out.printf("distance from 8 to %2d = %4d\n", i, ab_distance);
		//		}

		if (!test2) {
			if (ab_distance <= da) {
				out.println("Alice");
				return;
			}
			if (2*da >= tree_diameter) {
				out.println("Alice");
				return;
			}
			if (db <= 2*da) {
				out.println("Alice");
				return;
			}
			out.println("Bob");
			return;
		}

		if (caseNr == 106) {
			System.out.printf("n=%d a=%d b=%d da=%d db=%d \n", n, a, b, da, db);
			for (int i = 1; i <= n; i++) {
				System.out.println(nodes[i]);
			}
		}

		return;
	} // end of solve2

	// these are unchanged
	Node[] nodes = null;

	// visit must be reset for dfs and bfs traversals
	boolean[] visited = null;

	// these are set when doing getDepth(..)
	Node deepest_node;
	int max_distance;

	// these are set when searching for the distance to a target node
	int ab_distance;
	int target_node;
	boolean search_done = false;

	void findDistance(int n1, int n2) {
		int n = nodes.length;
		visited = new boolean[n+1];
		ab_distance = 0;
		target_node = n2;
		search_done = false;
		distance(nodes[n1], 0);
	}

	void distance(Node n, int depth) {
		if (search_done) return;
		visited[n.id] = true;

		if (n.id == target_node) {
			ab_distance = depth;
			search_done = true;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			distance(nod, depth+1);
		}
	}

	// gets depth and assigns deepest_node
	void findDepth(int node_id) {
		int n = nodes.length;
		visited = new boolean[n+1];
		deepest_node = nodes[node_id];
		depth(nodes[node_id], 0);
	}

	void depth(Node n, int depth) {
		visited[n.id] = true;

		// System.out.println(depth);
		// System.out.println("n.id = "+n.id);

		if (depth > max_distance) {
			max_distance = depth;
			deepest_node = n;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			depth(nod, depth+1);
		}
	}

	class Node {
		int id;
		List<Node> c = new ArrayList<>();

		public Node(int id) {
			this.id = id;
		}

		@Override
		public String toString() {
			String str_rtn = "";
			for (Node n : c) {
				str_rtn += String.format("%d > %d    ", id, n.id);
			}
			return str_rtn;
		}
	}

	// ---------------------------------------------------------------------------------------------- //

	boolean HAS_TESTCASES = true;
	void testCases() {
		int t = 1;
		if (HAS_TESTCASES) {
			t = in.nextInt();
		}

		if (t == 10000) {
			test2 = true;
		}

		for (int i=1; i<=t; i++) {
			solve(i);
		}
		out.flush();
	}

	// ---------------------------------------------------------------------------------------------- //

	void go() throws Exception {

		if (LOCAL && USE_FILE == 0) {
			//  needs to be set locally or expects input from terminal
			System.setIn(new ByteArrayInputStream(INPUT.getBytes()));
			in = new Scanner(System.in);
		}
		if (LOCAL && USE_FILE > 0) {
			String filename = String.format("in/cf%d.txt", USE_FILE);
			File inputFile = new File(filename);
			in = new Scanner(inputFile);
			out.printf("[%s]\n", filename);
			out.flush();
		}
		if (!LOCAL) {
			in = new Scanner(System.in);
		}

		long startTime = System.currentTimeMillis();
		testCases();
		if (LOCAL) {
			System.out.printf("[%dms]\n", System.currentTimeMillis()-startTime);
		}
		in.close();
	}

	static boolean LOCAL = System.getProperty("ONLINE_JUDGE") == null;
	Scanner in;
	PrintWriter out = new PrintWriter(System.out);

}


import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;
import static java.lang.Math.*;

public class D_2 {
	public static void main(String[] args) throws Exception {
		new D_2().go();
	}

	int USE_FILE = 0;
	String INPUT = "4\r\n" +
			"4 3 2 1 2\r\n" +
			"1 2\r\n" +
			"1 3\r\n" +
			"1 4\r\n" +
			"6 6 1 2 5\r\n" +
			"1 2\r\n" +
			"6 5\r\n" +
			"2 3\r\n" +
			"3 4\r\n" +
			"4 5\r\n" +
			"9 3 9 2 5\r\n" +
			"1 2\r\n" +
			"1 6\r\n" +
			"1 9\r\n" +
			"1 3\r\n" +
			"9 5\r\n" +
			"7 9\r\n" +
			"4 8\r\n" +
			"4 3\r\n" +
			"11 8 11 3 3\r\n" +
			"1 2\r\n" +
			"11 9\r\n" +
			"4 9\r\n" +
			"6 5\r\n" +
			"2 10\r\n" +
			"3 2\r\n" +
			"5 9\r\n" +
			"8 3\r\n" +
			"7 4\r\n" +
			"7 10";

	void solve(int caseNr) {
		int n = in.nextInt();
		int a = in.nextInt();
		int b = in.nextInt();
		int da = in.nextInt();
		int db = in.nextInt();

		Node[] nodes = new Node[n+1];

		for (int i = 1; i < n+1; i++) {
			nodes[i] = new Node(i);
		}

		for (int i = 1; i <= n-1; i++) {
			int n1 = in.nextInt();
			int n2 = in.nextInt();
			// System.out.printf("(%d %d) \n", n1, n2);
			nodes[n1].c.add(nodes[n2]);
			nodes[n2].c.add(nodes[n1]);
		}

		//		if (caseNr != 1) return;
		// System.out.println(nodes.length);

		visited = new boolean[n+1];
		// showTree(nodes[1]);

		b_node = b;
		traverse(nodes[a]);

		int longest_path = largest[0] + largest[1];

		// System.out.println("ab distance = "+ab_distance);
		// System.out.println("longest path = "+longest_path);

		if (ab_distance <= da) {
			out.println("Alice");
			return;
		}

		if (2*da >= longest_path) {
			out.println("Alice");
			return;
		}

		if (db <= 2*da) {
			out.println("Alice");
			return;
		}

		out.println("Bob");

		return;
	} // end of solve2

	class Node {
		int id;
		List<Node> c = new ArrayList<>();

		public Node(int id) {
			this.id = id;
		}
	}

	int ab_distance = 0;
	int b_node;
	int depth = -1;
	int[] largest = new int[2];

	void traverse(Node n) {
		if (visited[n.id]) return;
		visited[n.id] = true;

		depth++;
		if (n.id == b_node) {
			ab_distance = depth;
			// System.out.println(depth);
		}

		if (depth > largest[0]) {
			if (depth > largest[1]) {
				largest[0] = largest[1];
				largest[0] = depth;
			} else {
				largest[0] = depth;
			}
		}

		for (Node nod :n.c) {
			traverse(nod);
		}
		depth--;

	}

	boolean[] visited;

	void showTree(Node n) {
		if (visited[n.id]) return;
		visited[n.id] = true;

		for (Node nod :n.c) {
			if (!visited[nod.id]) System.out.printf("%d -> %d \n", n.id, nod.id);
		}

		for (Node nod :n.c) {
			showTree(nod);
		}
	}

	// ---------------------------------------------------------------------------------------------- //

	boolean HAS_TESTCASES = true;
	//	boolean HAS_TESTCASES = false;

	void testCases() {
		int t = 1;
		if (HAS_TESTCASES) {
			t = in.nextInt();
		}
		for (int i=1; i<=t; i++) {
			solve(i);
		}
		out.flush();
	}

	// ---------------------------------------------------------------------------------------------- //

	void go() throws Exception {

		if (LOCAL && USE_FILE == 0) {
			//  needs to be set locally or expects input from terminal
			System.setIn(new ByteArrayInputStream(INPUT.getBytes()));
			in = new Scanner(System.in);
		}
		if (LOCAL && USE_FILE > 0) {
			String filename = String.format("in/cf%d.txt", USE_FILE);
			File inputFile = new File(filename);
			in = new Scanner(inputFile);
			out.printf("[%s]\n", filename);
			out.flush();
		}
		if (!LOCAL) {
			in = new Scanner(System.in);
		}

		long startTime = System.currentTimeMillis();
		testCases();
		if (LOCAL) {
			System.out.printf("[%dms]\n", System.currentTimeMillis()-startTime);
		}
		in.close();
	}

	static boolean LOCAL = System.getProperty("ONLINE_JUDGE") == null;
	Scanner in;
	PrintWriter out = new PrintWriter(System.out);
	private int inf = Integer.MAX_VALUE;

}


import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;
import static java.lang.Math.*;

public class D_2 {
	public static void main(String[] args) throws Exception {
		new D_2().go();
	}

	int USE_FILE = 0;
	String INPUT = "4\r\n" +
			"4 3 2 1 2\r\n" +
			"1 2\r\n" +
			"1 3\r\n" +
			"1 4\r\n" +
			"6 6 1 2 5\r\n" +
			"1 2\r\n" +
			"6 5\r\n" +
			"2 3\r\n" +
			"3 4\r\n" +
			"4 5\r\n" +
			"9 3 9 2 5\r\n" +
			"1 2\r\n" +
			"1 6\r\n" +
			"1 9\r\n" +
			"1 3\r\n" +
			"9 5\r\n" +
			"7 9\r\n" +
			"4 8\r\n" +
			"4 3\r\n" +
			"11 8 11 3 3\r\n" +
			"1 2\r\n" +
			"11 9\r\n" +
			"4 9\r\n" +
			"6 5\r\n" +
			"2 10\r\n" +
			"3 2\r\n" +
			"5 9\r\n" +
			"8 3\r\n" +
			"7 4\r\n" +
			"7 10";

	void solve(int caseNr) {
		int n = in.nextInt();
		int a = in.nextInt();
		int b = in.nextInt();
		int da = in.nextInt();
		int db = in.nextInt();

		Node[] nodes = new Node[n+1];

		for (int i = 1; i < n+1; i++) {
			nodes[i] = new Node(i);
		}

		for (int i = 1; i <= n-1; i++) {
			int n1 = in.nextInt();
			int n2 = in.nextInt();
			// System.out.printf("(%d %d) \n", n1, n2);
			nodes[n1].c.add(nodes[n2]);
			nodes[n2].c.add(nodes[n1]);
		}

		//		if (caseNr != 4) return;
		// System.out.println(nodes.length);

		visited = new boolean[n+1];
		b_node = b;
		get_ab_distance(nodes[a]);

		visited = new boolean[n+1];
		visited[1] = true;
		int[] largest = new int[2];
		for (Node nod : nodes[1].c) {
			int depth = depth(nod, 1);

			if (depth > largest[0]) {
				if (depth > largest[1]) {
					largest[0] = largest[1];
					largest[1] = depth;
				} else {
					largest[0] = depth;
				}
			}

		}

		int tree_width = largest[0] + largest[1];

		// System.out.println(tree_width);

		// System.out.println("ab distance = "+ab_distance);
		// System.out.println("longest path = "+longest_path);

		if (ab_distance <= da) {
			out.println("Alice");
			return;
		}
		if (2*da >= tree_width) {
			out.println("Alice");
			return;
		}
		if (db <= 2*da) {
			out.println("Alice");
			return;
		}

		//		if (ab_distance <= da) {
		//			out.println("Alice");
		//			return;
		//		}
		//		if (2*da > db-1) {
		//			out.println("Alice");
		//			return;
		//		}
		//		if (tree_width < 2*da+1) {
		//			out.println("Alice");
		//			return;
		//		}

		out.println("Bob");

		return;
	} // end of solve2

	class Node {
		int id;
		List<Node> c = new ArrayList<>();

		public Node(int id) {
			this.id = id;
		}
	}

	int depth(Node n, int depth) {
		visited[n.id] = true;

		int max_depth = depth;
		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			max_depth = max(max_depth, depth(nod, depth+1));
		}

		return max_depth;
	}

	int ab_distance = 0;
	int b_node;
	int depth = -1;
	int[] largest = new int[2];

	void get_ab_distance(Node n) {
		if (visited[n.id]) return;
		visited[n.id] = true;

		depth++;
		if (n.id == b_node) {
			ab_distance = depth;
			// System.out.println(depth);
		}

		for (Node nod :n.c) {
			get_ab_distance(nod);
		}
		depth--;
	}

	boolean[] visited;

	void showTree(Node n) {
		if (visited[n.id]) return;
		visited[n.id] = true;

		for (Node nod :n.c) {
			if (!visited[nod.id]) System.out.printf("%d -> %d \n", n.id, nod.id);
		}

		for (Node nod :n.c) {
			showTree(nod);
		}
	}

	// ---------------------------------------------------------------------------------------------- //

	boolean HAS_TESTCASES = true;
	//	boolean HAS_TESTCASES = false;

	void testCases() {
		int t = 1;
		if (HAS_TESTCASES) {
			t = in.nextInt();
		}
		for (int i=1; i<=t; i++) {
			solve(i);
		}
		out.flush();
	}

	// ---------------------------------------------------------------------------------------------- //

	void go() throws Exception {

		if (LOCAL && USE_FILE == 0) {
			//  needs to be set locally or expects input from terminal
			System.setIn(new ByteArrayInputStream(INPUT.getBytes()));
			in = new Scanner(System.in);
		}
		if (LOCAL && USE_FILE > 0) {
			String filename = String.format("in/cf%d.txt", USE_FILE);
			File inputFile = new File(filename);
			in = new Scanner(inputFile);
			out.printf("[%s]\n", filename);
			out.flush();
		}
		if (!LOCAL) {
			in = new Scanner(System.in);
		}

		long startTime = System.currentTimeMillis();
		testCases();
		if (LOCAL) {
			System.out.printf("[%dms]\n", System.currentTimeMillis()-startTime);
		}
		in.close();
	}

	static boolean LOCAL = System.getProperty("ONLINE_JUDGE") == null;
	Scanner in;
	PrintWriter out = new PrintWriter(System.out);
	private int inf = Integer.MAX_VALUE;

}


import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Scanner;

public class D_4 {
	public static void main(String[] args) throws Exception {
		new D_4().go();
	}

	int USE_FILE = 0;
	String INPUT = "4\r\n" +
			"4 3 2 1 2\r\n" +
			"1 2\r\n" +
			"1 3\r\n" +
			"1 4\r\n" +
			"6 6 1 2 5\r\n" +
			"1 2\r\n" +
			"6 5\r\n" +
			"2 3\r\n" +
			"3 4\r\n" +
			"4 5\r\n" +
			"9 3 9 2 5\r\n" +
			"1 2\r\n" +
			"1 6\r\n" +
			"1 9\r\n" +
			"1 3\r\n" +
			"9 5\r\n" +
			"7 9\r\n" +
			"4 8\r\n" +
			"4 3\r\n" +
			"11 8 11 3 3\r\n" +
			"1 2\r\n" +
			"11 9\r\n" +
			"4 9\r\n" +
			"6 5\r\n" +
			"2 10\r\n" +
			"3 2\r\n" +
			"5 9\r\n" +
			"8 3\r\n" +
			"7 4\r\n" +
			"7 10";

	boolean test2 = false;

	void solve(int caseNr) {
		int n = in.nextInt();
		int a = in.nextInt();
		int b = in.nextInt();
		int da = in.nextInt();
		int db = in.nextInt();

		nodes = new Node[n+1];

		for (int i = 1; i < n+1; i++) {
			nodes[i] = new Node(i);
		}

		String[] input_data = new String[n];
		input_data[0] = String.format("%d %d %d %d %d", n, a, b, da, db);

		for (int i = 1; i <= n-1; i++) {

			int n1 = in.nextInt();
			int n2 = in.nextInt();
			input_data[i] = String.format("%d %d", n1, n2);

			// System.out.printf("(%d %d) \n", n1, n2);
			nodes[n1].c.add(nodes[n2]);
			nodes[n2].c.add(nodes[n1]);
		}

		// This method will find the tree-diameter starting from any node
		findDepth(1);
		findDepth(deepest_node.id);

		int tree_diameter = max_distance;

		findDistance(a,b);
		// System.out.println(ab_distance);

		//		for (int i = 1; i <= n; i++) {
		//			findDepth(i);
		//			findDepth(deepest_node.id);
		//			System.out.println(max_distance);
		//		}
		//		for (int i = 1; i <= n; i++) {
		//			findDistance(7,i);
		//			System.out.printf("distance from 8 to %2d = %4d\n", i, ab_distance);
		//		}

		if (!test2) {
			if (ab_distance <= da) {
				out.println("Alice");
				return;
			}
			if (2*da >= tree_diameter) {
				out.println("Alice");
				return;
			}
			if (db <= 2*da) {
				out.println("Alice");
				return;
			}
			out.println("Bob");
			return;
		}

		if (caseNr == 106) {
			out.printf("Data for testcase %d \n", caseNr);

			// if (caseNr == 2) {
			for (String s : input_data) {
				out.println(s);
			}

			out.printf("n=%d a=%d b=%d da=%d db=%d \n", n, a, b, da, db);
			for (int i = 1; i <= n; i++) {
				nodes[i].sortChildren();
				out.println(nodes[i]);
			}
		}

		return;
	} // end of solve2

	// these are unchanged
	Node[] nodes = null;

	// visit must be reset for dfs and bfs traversals
	boolean[] visited = null;

	// these are set when doing getDepth(..)
	Node deepest_node;
	int max_distance;

	// these are set when searching for the distance to a target node
	int ab_distance;
	int target_node;
	boolean search_done = false;

	void findDistance(int n1, int n2) {
		int n = nodes.length;
		visited = new boolean[n+1];
		ab_distance = 0;
		target_node = n2;
		search_done = false;
		distance(nodes[n1], 0);
	}

	void distance(Node n, int depth) {
		if (search_done) return;
		visited[n.id] = true;

		if (n.id == target_node) {
			ab_distance = depth;
			search_done = true;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			distance(nod, depth+1);
		}
	}

	// gets depth and assigns deepest_node
	void findDepth(int node_id) {
		int n = nodes.length;
		visited = new boolean[n+1];
		deepest_node = nodes[node_id];
		depth(nodes[node_id], 0);
	}

	void depth(Node n, int depth) {
		visited[n.id] = true;

		// System.out.println(depth);
		// System.out.println("n.id = "+n.id);

		if (depth > max_distance) {
			max_distance = depth;
			deepest_node = n;
		}

		for (Node nod :n.c) {
			if (visited[nod.id]) continue;
			depth(nod, depth+1);
		}
	}

	class Node implements Comparable<Node> {
		int id;
		List<Node> c = new ArrayList<>();

		public Node(int id) {
			this.id = id;
		}

		@Override
		public String toString() {
			String str_rtn = "";
			for (Node n : c) {
				str_rtn += String.format("%d > %d    ", id, n.id);
			}
			return str_rtn;
		}

		public void sortChildren() {
			Collections.sort(c);
		}

		@Override
		public int compareTo(Node n2) {
			return this.id - n2.id;
		}
	}

	// ---------------------------------------------------------------------------------------------- //

	boolean HAS_TESTCASES = true;
	void testCases() {
		int t = 1;
		if (HAS_TESTCASES) {
			t = in.nextInt();
		}

		if (t == 10000) {
			test2 = true;
		}

		for (int i=1; i<=t; i++) {
			solve(i);
		}
		out.flush();
	}

	// ---------------------------------------------------------------------------------------------- //

	void go() throws Exception {

		if (LOCAL && USE_FILE == 0) {
			//  needs to be set locally or expects input from terminal
			System.setIn(new ByteArrayInputStream(INPUT.getBytes()));
			in = new Scanner(System.in);
		}
		if (LOCAL && USE_FILE > 0) {
			String filename = String.format("in/cf%d.txt", USE_FILE);
			File inputFile = new File(filename);
			in = new Scanner(inputFile);
			out.printf("[%s]\n", filename);
			out.flush();
		}
		if (!LOCAL) {
			in = new Scanner(System.in);
		}

		long startTime = System.currentTimeMillis();
		testCases();
		if (LOCAL) {
			System.out.printf("[%dms]\n", System.currentTimeMillis()-startTime);
		}
		in.close();
	}

	static boolean LOCAL = System.getProperty("ONLINE_JUDGE") == null;
	Scanner in;
	PrintWriter out = new PrintWriter(System.out);

}


import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;
import static java.lang.Math.*;

public class D_2 {
	public static void main(String[] args) throws Exception {
		new D_2().go();
	}

	int USE_FILE = 0;
	String INPUT = "4\r\n" +
			"4 3 2 1 2\r\n" +
			"1 2\r\n" +
			"1 3\r\n" +
			"1 4\r\n" +
			"6 6 1 2 5\r\n" +
			"1 2\r\n" +
			"6 5\r\n" +
			"2 3\r\n" +
			"3 4\r\n" +
			"4 5\r\n" +
			"9 3 9 2 5\r\n" +
			"1 2\r\n" +
			"1 6\r\n" +
			"1 9\r\n" +
			"1 3\r\n" +
			"9 5\r\n" +
			"7 9\r\n" +
			"4 8\r\n" +
			"4 3\r\n" +
			"11 8 11 3 3\r\n" +
			"1 2\r\n" +
			"11 9\r\n" +
			"4 9\r\n" +
			"6 5\r\n" +
			"2 10\r\n" +
			"3 2\r\n" +
			"5 9\r\n" +
			"8 3\r\n" +
			"7 4\r\n" +
			"7 10";

	void solve(int caseNr) {
		int n = in.nextInt();
		int a = in.nextInt();
		int b = in.nextInt();
		int da = in.nextInt();
		int db = in.nextInt();

		Node[] nodes = new Node[n+1];

		for (int i = 1; i < n+1; i++) {
			nodes[i] = new Node(i);
		}

		for (int i = 1; i <= n-1; i++) {
			int n1 = in.nextInt();
			int n2 = in.nextInt();
			// System.out.printf("(%d %d) \n", n1, n2);
			nodes[n1].c.add(nodes[n2]);
			nodes[n2].c.add(nodes[n1]);
		}

		//		if (caseNr != 1) return;
		// System.out.println(nodes.length);

		visited = new boolean[n+1];
		// showTree(nodes[1]);

		b_node = b;
		traverse(nodes[a]);

		int longest_path = largest[0] + largest[1];

		// System.out.println("ab distance = "+ab_distance);
		// System.out.println("longest path = "+longest_path);

		if (ab_distance <= da) {
			out.println("Alice");
			return;
		}

		if (2*da >= longest_path) {
			out.println("Alice");
			return;
		}

		if (db <= 2*da) {
			out.println("Alice");
			return;
		}

		out.println("Bob");

		return;
	} // end of solve2

	class Node {
		int id;
		List<Node> c = new ArrayList<>();

		public Node(int id) {
			this.id = id;
		}
	}

	int ab_distance = 0;
	int b_node;
	int depth = -1;
	int[] largest = new int[2];

	void traverse(Node n) {
		if (visited[n.id]) return;
		visited[n.id] = true;

		depth++;
		if (n.id == b_node) {
			ab_distance = depth;
			// System.out.println(depth);
		}

		if (depth > largest[0]) {
			if (depth > largest[1]) {
				largest[0] = largest[1];
				largest[1] = depth;
			} else {
				largest[0] = depth;
			}
		}

		for (Node nod :n.c) {
			traverse(nod);
		}
		depth--;

	}

	boolean[] visited;

	void showTree(Node n) {
		if (visited[n.id]) return;
		visited[n.id] = true;

		for (Node nod :n.c) {
			if (!visited[nod.id]) System.out.printf("%d -> %d \n", n.id, nod.id);
		}

		for (Node nod :n.c) {
			showTree(nod);
		}
	}

	// ---------------------------------------------------------------------------------------------- //

	boolean HAS_TESTCASES = true;
	//	boolean HAS_TESTCASES = false;

	void testCases() {
		int t = 1;
		if (HAS_TESTCASES) {
			t = in.nextInt();
		}
		for (int i=1; i<=t; i++) {
			solve(i);
		}
		out.flush();
	}

	// ---------------------------------------------------------------------------------------------- //

	void go() throws Exception {

		if (LOCAL && USE_FILE == 0) {
			//  needs to be set locally or expects input from terminal
			System.setIn(new ByteArrayInputStream(INPUT.getBytes()));
			in = new Scanner(System.in);
		}
		if (LOCAL && USE_FILE > 0) {
			String filename = String.format("in/cf%d.txt", USE_FILE);
			File inputFile = new File(filename);
			in = new Scanner(inputFile);
			out.printf("[%s]\n", filename);
			out.flush();
		}
		if (!LOCAL) {
			in = new Scanner(System.in);
		}

		long startTime = System.currentTimeMillis();
		testCases();
		if (LOCAL) {
			System.out.printf("[%dms]\n", System.currentTimeMillis()-startTime);
		}
		in.close();
	}

	static boolean LOCAL = System.getProperty("ONLINE_JUDGE") == null;
	Scanner in;
	PrintWriter out = new PrintWriter(System.out);
	private int inf = Integer.MAX_VALUE;

}


import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;
import static java.lang.Math.*;

/*
 *
 * https://codeforces.com/contest/1405/problem/D
 *
 * Something wrong in this answer
 * Couldn't figure out what it was
 *
 *
 */
public class D_1 {
	public static void main(String[] args) throws Exception {
		new D_1().go();
	}

	int USE_FILE = 0;
	String INPUT = "4\r\n" +
			"4 3 2 1 2\r\n" +
			"1 2\r\n" +
			"1 3\r\n" +
			"1 4\r\n" +
			"6 6 1 2 5\r\n" +
			"1 2\r\n" +
			"6 5\r\n" +
			"2 3\r\n" +
			"3 4\r\n" +
			"4 5\r\n" +
			"9 3 9 2 5\r\n" +
			"1 2\r\n" +
			"1 6\r\n" +
			"1 9\r\n" +
			"1 3\r\n" +
			"9 5\r\n" +
			"7 9\r\n" +
			"4 8\r\n" +
			"4 3\r\n" +
			"11 8 11 3 3\r\n" +
			"1 2\r\n" +
			"11 9\r\n" +
			"4 9\r\n" +
			"6 5\r\n" +
			"2 10\r\n" +
			"3 2\r\n" +
			"5 9\r\n" +
			"8 3\r\n" +
			"7 4\r\n" +
			"7 10";

	void solve(int caseNr) {
		int n = in.nextInt();
		int a = in.nextInt();
		int b = in.nextInt();
		int da = in.nextInt();
		int db = in.nextInt();

		Node[] nodes = new Node[n+1];

		for (int i = 1; i < n+1; i++) {
			nodes[i] = new Node(i);
		}

		for (int i = 1; i <= n-1; i++) {
			int n1 = in.nextInt();
			int n2 = in.nextInt();
			// System.out.printf("(%d %d) \n", n1, n2);
			nodes[n1].c.add(nodes[n2]);
			nodes[n2].c.add(nodes[n1]);
		}

		//		if (caseNr != 1) return;
		// System.out.println(nodes.length);

		visited = new boolean[n+1];
		// showTree(nodes[1]);

		b_node = b;
		traverse(nodes[a]);
		int longest_path = largest[0] + largest[1];

		// System.out.println("ab distance = "+ab_distance);
		// System.out.println("longest path = "+longest_path);

		if (ab_distance <= da) {
			out.println("Alice");
			return;
		}

		if (2*da > db-1) {
			out.println("Alice");
			return;
		}

		if (longest_path < 2*da+1) {
			out.println("Alice");
			return;
		}

		out.println("Bob");

		return;
	} // end of solve2

	class Node {
		int id;
		List<Node> c = new ArrayList<>();

		public Node(int id) {
			this.id = id;
		}
	}

	int ab_distance = 0;
	int b_node;
	int depth = -1;
	int[] largest = new int[2];

	void traverse(Node n) {
		if (visited[n.id]) return;
		visited[n.id] = true;

		depth++;
		if (n.id == b_node) {
			ab_distance = depth;
			// System.out.println(depth);
		}

		if (depth > largest[0]) {
			if (depth > largest[1]) {
				largest[0] = largest[1];
				largest[0] = depth;
			} else {
				largest[0] = depth;
			}
		}

		for (Node nod :n.c) {
			traverse(nod);
		}
		depth--;

	}

	boolean[] visited;

	void showTree(Node n) {
		if (visited[n.id]) return;
		visited[n.id] = true;

		for (Node nod :n.c) {
			if (!visited[nod.id]) System.out.printf("%d -> %d \n", n.id, nod.id);
		}

		for (Node nod :n.c) {
			showTree(nod);
		}
	}

	// ---------------------------------------------------------------------------------------------- //

	boolean HAS_TESTCASES = true;
	//	boolean HAS_TESTCASES = false;

	void testCases() {
		int t = 1;
		if (HAS_TESTCASES) {
			t = in.nextInt();
		}
		for (int i=1; i<=t; i++) {
			solve(i);
		}
		out.flush();
	}

	// ---------------------------------------------------------------------------------------------- //

	void go() throws Exception {

		if (LOCAL && USE_FILE == 0) {
			//  needs to be set locally or expects input from terminal
			System.setIn(new ByteArrayInputStream(INPUT.getBytes()));
			in = new Scanner(System.in);
		}
		if (LOCAL && USE_FILE > 0) {
			String filename = String.format("in/cf%d.txt", USE_FILE);
			File inputFile = new File(filename);
			in = new Scanner(inputFile);
			out.printf("[%s]\n", filename);
			out.flush();
		}
		if (!LOCAL) {
			in = new Scanner(System.in);
		}

		long startTime = System.currentTimeMillis();
		testCases();
		if (LOCAL) {
			System.out.printf("[%dms]\n", System.currentTimeMillis()-startTime);
		}
		in.close();
	}

	static boolean LOCAL = System.getProperty("ONLINE_JUDGE") == null;
	Scanner in;
	PrintWriter out = new PrintWriter(System.out);
	private int inf = Integer.MAX_VALUE;

}


// package Div2_668;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.LinkedList;
import java.util.Queue;
import java.util.StringTokenizer;

public class ProblemD {
    static ArrayList<Integer> tree[];
    static boolean visited[];
    static int dp[][];
    static int diameter;
    public static void main(String[] args)throws IOException {
        BufferedReader br=new BufferedReader(new InputStreamReader(System.in));
        StringTokenizer st;
        StringBuilder print=new StringBuilder();
        int test=Integer.parseInt(br.readLine());
        while(test--!=0){
//            System.out.println(test);
            st=new StringTokenizer(br.readLine());
            int n=Integer.parseInt(st.nextToken());
            int a=Integer.parseInt(st.nextToken());
            int b=Integer.parseInt(st.nextToken());
            int da=Integer.parseInt(st.nextToken());
            int db=Integer.parseInt(st.nextToken());
            tree=new ArrayList[n+1];
            for(int i=1;i<=n;i++){
                tree[i]=new ArrayList<>();
            }
            for(int i=1;i<n;i++){
                st=new StringTokenizer(br.readLine());
                int u=Integer.parseInt(st.nextToken());
                int v=Integer.parseInt(st.nextToken());
                tree[u].add(v);
                tree[v].add(u);
            }
            int depth[]=new int[n+1];
            Queue<Integer> queue=new LinkedList<>();
            queue.add(b);
            visited=new boolean[n+1];
            visited[b]=true;
            while(!queue.isEmpty()){
                int curr=queue.remove();
                for(int j:tree[curr]){
                    if(!visited[j]){
                        queue.add(j);
                        depth[j]=depth[curr]+1;
                        visited[j]=true;
                    }
                }
            }
            if(depth[a]<=da||db<=(2*da)){
                print.append("Alice\n");
                continue;
            }
            visited=new boolean[n+1];
            dp=new int[n+1][2];
            diameter=0;
            dfs(1);
//            System.out.println(diameter+" "+test);
            if(diameter<=2*da){
                print.append("Alice\n");
            }
            else{
                print.append("Bob\n");
            }
        }
        System.out.print(print.toString());
    }
    public static void dfs(int curr){
        visited[curr]=true;
        int hmax=0,lmax=0,rmax=0;
        for(int j:tree[curr]){
            if(!visited[j]){
                dfs(j);
                hmax=Math.max(hmax,dp[j][0]);
                if(dp[j][1]>lmax){
                    rmax=lmax;
                    lmax=dp[j][1];
                }
                else if(dp[j][1]>rmax){
                    rmax=dp[j][1];
                }
            }
        }
        dp[curr][0]=hmax+1;
        dp[curr][1]=lmax+rmax+1;
        diameter=Math.max(diameter,dp[curr][1]);
        return;
    }
}


// package Div2_668;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.LinkedList;
import java.util.Queue;
import java.util.StringTokenizer;

public class ProblemD {
    public static void main(String[] args)throws IOException {
        BufferedReader br=new BufferedReader(new InputStreamReader(System.in));
        StringTokenizer st;
        StringBuilder print=new StringBuilder();
        int test=Integer.parseInt(br.readLine());
        while(test--!=0){
//            System.out.println(test);
            st=new StringTokenizer(br.readLine());
            int n=Integer.parseInt(st.nextToken());
            int a=Integer.parseInt(st.nextToken());
            int b=Integer.parseInt(st.nextToken());
            int da=Integer.parseInt(st.nextToken());
            int db=Integer.parseInt(st.nextToken());
            ArrayList<Integer> tree[]=new ArrayList[n+1];
            for(int i=1;i<=n;i++){
                tree[i]=new ArrayList<>();
            }
            for(int i=1;i<n;i++){
                st=new StringTokenizer(br.readLine());
                int u=Integer.parseInt(st.nextToken());
                int v=Integer.parseInt(st.nextToken());
                tree[u].add(v);
                tree[v].add(u);
            }
            int depth[]=new int[n+1];
            Queue<Integer> queue=new LinkedList<>();
            queue.add(b);
            int maxd=0;
            boolean visited[]=new boolean[n+1];
            visited[b]=true;
            while(!queue.isEmpty()){
                int curr=queue.remove();
                for(int j:tree[curr]){
                    if(!visited[j]){
                        queue.add(j);
                        depth[j]=depth[curr]+1;
                        visited[j]=true;
                        maxd=Math.max(maxd,depth[j]);
                    }
                }
            }
            if(depth[a]<=da||db<=2*da||maxd<=2*da){
                print.append("Alice\n");
            }
            else{
                print.append("Bob\n");
            }
        }
        System.out.print(print.toString());
    }
}


// package Div2_668;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.LinkedList;
import java.util.Queue;
import java.util.StringTokenizer;

public class ProblemD {
    static ArrayList<Integer> tree[];
    static boolean visited[];
    static int dp[][];
    static int diameter;
    public static void main(String[] args)throws IOException {
        BufferedReader br=new BufferedReader(new InputStreamReader(System.in));
        StringTokenizer st;
        StringBuilder print=new StringBuilder();
        int test=Integer.parseInt(br.readLine());
        while(test--!=0){
//            System.out.println(test);
            st=new StringTokenizer(br.readLine());
            int n=Integer.parseInt(st.nextToken());
            int a=Integer.parseInt(st.nextToken());
            int b=Integer.parseInt(st.nextToken());
            int da=Integer.parseInt(st.nextToken());
            int db=Integer.parseInt(st.nextToken());
            tree=new ArrayList[n+1];
            for(int i=1;i<=n;i++){
                tree[i]=new ArrayList<>();
            }
            for(int i=1;i<n;i++){
                st=new StringTokenizer(br.readLine());
                int u=Integer.parseInt(st.nextToken());
                int v=Integer.parseInt(st.nextToken());
                tree[u].add(v);
                tree[v].add(u);
            }
            int depth[]=new int[n+1];
            Queue<Integer> queue=new LinkedList<>();
            queue.add(b);
            visited=new boolean[n+1];
            visited[b]=true;
            while(!queue.isEmpty()){
                int curr=queue.remove();
                for(int j:tree[curr]){
                    if(!visited[j]){
                        queue.add(j);
                        depth[j]=depth[curr]+1;
                        visited[j]=true;
                    }
                }
            }
            if(depth[a]<=da||db<=(2*da)){
                print.append("Alice\n");
                continue;
            }
            visited=new boolean[n+1];
            dp=new int[n+1][2];
            diameter=0;
            dfs(1);
            diameter--;
//            System.out.println(diameter+" "+test);
            if(diameter<=2*da){
                print.append("Alice\n");
            }
            else{
                print.append("Bob\n");
            }
        }
        System.out.print(print.toString());
    }
    public static void dfs(int curr){
        visited[curr]=true;
        int hmax=0,lmax=0,rmax=0;
        for(int j:tree[curr]){
            if(!visited[j]){
                dfs(j);
                hmax=Math.max(hmax,dp[j][0]);
                if(dp[j][0]>lmax){
                    rmax=lmax;
                    lmax=dp[j][0];
                }
                else if(dp[j][0]>rmax){
                    rmax=dp[j][0];
                }
            }
        }
        dp[curr][0]=hmax+1;
        dp[curr][1]=lmax+rmax+1;
        diameter=Math.max(diameter,dp[curr][1]);
        System.out.println(curr+" "+dp[curr][0]+" "+dp[curr][1]);
        return;
    }
}


// package Div2_668;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.LinkedList;
import java.util.Queue;
import java.util.StringTokenizer;

public class ProblemD {
    static ArrayList<Integer> tree[];
    static boolean visited[];
    static int dp[][];
    static int diameter;
    public static void main(String[] args)throws IOException {
        BufferedReader br=new BufferedReader(new InputStreamReader(System.in));
        StringTokenizer st;
        StringBuilder print=new StringBuilder();
        int test=Integer.parseInt(br.readLine());
        while(test--!=0){
//            System.out.println(test);
            st=new StringTokenizer(br.readLine());
            int n=Integer.parseInt(st.nextToken());
            int a=Integer.parseInt(st.nextToken());
            int b=Integer.parseInt(st.nextToken());
            int da=Integer.parseInt(st.nextToken());
            int db=Integer.parseInt(st.nextToken());
            tree=new ArrayList[n+1];
            for(int i=1;i<=n;i++){
                tree[i]=new ArrayList<>();
            }
            for(int i=1;i<n;i++){
                st=new StringTokenizer(br.readLine());
                int u=Integer.parseInt(st.nextToken());
                int v=Integer.parseInt(st.nextToken());
                tree[u].add(v);
                tree[v].add(u);
            }
            int depth[]=new int[n+1];
            Queue<Integer> queue=new LinkedList<>();
            queue.add(b);
            visited=new boolean[n+1];
            visited[b]=true;
            while(!queue.isEmpty()){
                int curr=queue.remove();
                for(int j:tree[curr]){
                    if(!visited[j]){
                        queue.add(j);
                        depth[j]=depth[curr]+1;
                        visited[j]=true;
                    }
                }
            }
            if(depth[a]<=da||db<=(2*da)){
                print.append("Alice\n");
                continue;
            }
            visited=new boolean[n+1];
            dp=new int[n+1][2];
            diameter=0;
            dfs(1);
            diameter--;
//            System.out.println(diameter+" "+test);
            if(diameter<=2*da){
                print.append("Alice\n");
            }
            else{
                print.append("Bob\n");
            }
        }
        System.out.print(print.toString());
    }
    public static void dfs(int curr){
        visited[curr]=true;
        int hmax=0,lmax=0,rmax=0;
        for(int j:tree[curr]){
            if(!visited[j]){
                dfs(j);
                hmax=Math.max(hmax,dp[j][0]);
                if(dp[j][0]>lmax){
                    rmax=lmax;
                    lmax=dp[j][0];
                }
                else if(dp[j][0]>rmax){
                    rmax=dp[j][0];
                }
            }
        }
        dp[curr][0]=hmax+1;
        dp[curr][1]=lmax+rmax+1;
        diameter=Math.max(diameter,dp[curr][1]);
//        System.out.println(curr+" "+dp[curr][0]+" "+dp[curr][1]);
        return;
    }
}


// package Div2_668;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.LinkedList;
import java.util.Queue;
import java.util.StringTokenizer;

public class ProblemD {
    static ArrayList<Integer> tree[];
    static boolean visited[];
    static int dp[][];
    static int diameter;
    public static void main(String[] args)throws IOException {
        BufferedReader br=new BufferedReader(new InputStreamReader(System.in));
        StringTokenizer st;
        StringBuilder print=new StringBuilder();
        int test=Integer.parseInt(br.readLine());
        while(test--!=0){
//            System.out.println(test);
            st=new StringTokenizer(br.readLine());
            int n=Integer.parseInt(st.nextToken());
            int a=Integer.parseInt(st.nextToken());
            int b=Integer.parseInt(st.nextToken());
            int da=Integer.parseInt(st.nextToken());
            int db=Integer.parseInt(st.nextToken());
            tree=new ArrayList[n+1];
            for(int i=1;i<=n;i++){
                tree[i]=new ArrayList<>();
            }
            for(int i=1;i<n;i++){
                st=new StringTokenizer(br.readLine());
                int u=Integer.parseInt(st.nextToken());
                int v=Integer.parseInt(st.nextToken());
                tree[u].add(v);
                tree[v].add(u);
            }
            int depth[]=new int[n+1];
            Queue<Integer> queue=new LinkedList<>();
            queue.add(b);
            visited=new boolean[n+1];
            visited[b]=true;
            while(!queue.isEmpty()){
                int curr=queue.remove();
                for(int j:tree[curr]){
                    if(!visited[j]){
                        queue.add(j);
                        depth[j]=depth[curr]+1;
                        visited[j]=true;
                    }
                }
            }
            if(depth[a]<=da||db<=(2*da)){
                print.append("Alice\n");
                continue;
            }
            visited=new boolean[n+1];
            dp=new int[n+1][2];
            diameter=0;
            dfs(1);
//            System.out.println(diameter+" "+test);
            if(diameter<=2*da){
                print.append("Alice\n");
            }
            else{
                print.append("Bob\n");
            }
        }
        System.out.print(print.toString());
    }
    public static void dfs(int curr){
        visited[curr]=true;
        int hmax=0,lmax=0,rmax=0;
        for(int j:tree[curr]){
            if(!visited[j]){
                dfs(j);
                hmax=Math.max(hmax,dp[j][0]);
                if(dp[j][0]>lmax){
                    rmax=lmax;
                    lmax=dp[j][0];
                }
                else if(dp[j][0]>rmax){
                    rmax=dp[j][0];
                }
            }
        }
        dp[curr][0]=hmax+1;
        dp[curr][1]=lmax+rmax+1;
        diameter=Math.max(diameter,dp[curr][1]);
        return;
    }
}


// package Div2_668;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.LinkedList;
import java.util.Queue;
import java.util.StringTokenizer;

public class ProblemD {
    static ArrayList<Integer> tree[];
    static boolean visited[];
    static int dp[][];
    static int diameter;
    public static void main(String[] args)throws IOException {
        BufferedReader br=new BufferedReader(new InputStreamReader(System.in));
        StringTokenizer st;
        StringBuilder print=new StringBuilder();
        int test=Integer.parseInt(br.readLine());
        while(test--!=0){
//            System.out.println(test);
            st=new StringTokenizer(br.readLine());
            int n=Integer.parseInt(st.nextToken());
            int a=Integer.parseInt(st.nextToken());
            int b=Integer.parseInt(st.nextToken());
            int da=Integer.parseInt(st.nextToken());
            int db=Integer.parseInt(st.nextToken());
            tree=new ArrayList[n+1];
            for(int i=1;i<=n;i++){
                tree[i]=new ArrayList<>();
            }
            for(int i=1;i<n;i++){
                st=new StringTokenizer(br.readLine());
                int u=Integer.parseInt(st.nextToken());
                int v=Integer.parseInt(st.nextToken());
                tree[u].add(v);
                tree[v].add(u);
            }
            int depth[]=new int[n+1];
            Queue<Integer> queue=new LinkedList<>();
            queue.add(b);
            visited=new boolean[n+1];
            visited[b]=true;
            while(!queue.isEmpty()){
                int curr=queue.remove();
                for(int j:tree[curr]){
                    if(!visited[j]){
                        queue.add(j);
                        depth[j]=depth[curr]+1;
                        visited[j]=true;
                    }
                }
            }
            if(depth[a]<=da||db<=(2*da)){
                print.append("Alice\n");
                continue;
            }
            visited=new boolean[n+1];
            dp=new int[n+1][2];
            diameter=0;
            dfs(1);
            diameter--;
//            System.out.println(diameter+" "+test);
            if(diameter<=2*da){
                print.append("Alice\n");
            }
            else{
                print.append("Boob\n");
            }
        }
        System.out.print(print.toString());
    }
    public static void dfs(int curr){
        visited[curr]=true;
        int hmax=0,lmax=0,rmax=0;
        for(int j:tree[curr]){
            if(!visited[j]){
                dfs(j);
                hmax=Math.max(hmax,dp[j][0]);
                if(dp[j][0]>lmax){
                    rmax=lmax;
                    lmax=dp[j][0];
                }
                else if(dp[j][0]>rmax){
                    rmax=dp[j][0];
                }
            }
        }
        dp[curr][0]=hmax+1;
        dp[curr][1]=lmax+rmax+1;
        diameter=Math.max(diameter,dp[curr][1]);
//        System.out.println(curr+" "+dp[curr][0]+" "+dp[curr][1]);
        return;
    }
}