1 /*	$OpenBSD: tutor.c,v 1.10 2023/05/05 10:26:50 tb Exp $	*/
2 
3 /*
4  * Copyright (c) 1980, 1993
5  *	The Regents of the University of California.  All rights reserved.
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  * 1. Redistributions of source code must retain the above copyright
11  *    notice, this list of conditions and the following disclaimer.
12  * 2. Redistributions in binary form must reproduce the above copyright
13  *    notice, this list of conditions and the following disclaimer in the
14  *    documentation and/or other materials provided with the distribution.
15  * 3. Neither the name of the University nor the names of its contributors
16  *    may be used to endorse or promote products derived from this software
17  *    without specific prior written permission.
18  *
19  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
20  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
23  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
24  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
25  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
26  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
27  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
28  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
29  * SUCH DAMAGE.
30  */
31 
32 #include "back.h"
33 #include "tutor.h"
34 
35 static const char better[] = "That is a legal move, but there is a better one.\n";
36 
37 __dead void
tutor(void)38 tutor(void)
39 {
40 	int     i, j, k;
41 	int     wrongans;
42 
43 	wrongans = 0;
44 	i = 0;
45 	begscr = 18;
46 	cturn = -1;
47 	home = 0;
48 	bar = 25;
49 	inptr = &in[0];
50 	inopp = &in[1];
51 	offptr = &off[0];
52 	offopp = &off[1];
53 	Colorptr = &color[0];
54 	colorptr = &color[2];
55 	colen = 5;
56 	wrboard();
57 
58 	while (1) {
59 		if (!brdeq(test[i].brd, board)) {
60 			wrongans++;
61 			move(18, 0);
62 			if (wrongans >= 3) {
63 				wrongans = 0;
64 				text(*test[i].ans);
65 				memcpy(board,test[i].brd,26*sizeof(int));
66 				/* and have to fix *inptr, *offptr; player is red (+ve) */
67 				k = 0;
68 				for (j = 19; j < 26; j++)
69 					k += (board[j] > 0 ? board[j] : 0);
70 				*inopp = k;
71 				for (j = 0; j < 19; j++)
72 					k += (board[j] > 0 ? board[j] : 0);
73 				*offopp = k - 30;  /* -15 at start */
74 				moveplayers();
75 				clrest();
76 			} else {
77 				addstr(better);
78 				nexturn();
79 				movback(mvlim);
80 				moveplayers();
81 				clrest();
82 				getyx(stdscr, j, k);
83 				if (j == 19) {
84 					proll();
85 					addch('\t');
86 				} else
87 					move(j > 19 ? j - 2 : j + 4, 25);
88 				getmove();
89 				if (cturn == 0)
90 					leave();
91 				continue;
92 			}
93 		} else
94 			wrongans = 0;
95 		move(18, 0);
96 		text(*test[i].com);
97 		move(19, 0);
98 		if (i == maxmoves)
99 			break;
100 		D0 = test[i].roll1;
101 		D1 = test[i].roll2;
102 		d0 = 0;
103 		mvlim = 0;
104 		for (j = 0; j < 4; j++) {
105 			if (test[i].mp[j] == test[i].mg[j])
106 				break;
107 			p[j] = test[i].mp[j];
108 			g[j] = test[i].mg[j];
109 			mvlim++;
110 		}
111 		if (mvlim)
112 			for (j = 0; j < mvlim; j++)
113 				if (makmove(j))
114 					addstr("AARGH!!!\n");
115 		moveplayers();
116 		nexturn();
117 		D0 = test[i].new1;
118 		D1 = test[i].new2;
119 		d0 = 0;
120 		i++;
121 		mvlim = movallow();
122 		if (mvlim) {
123 			clrest();
124 			proll();
125 			addch('\t');
126 			getmove();
127 			moveplayers();
128 			if (cturn == 0)
129 				leave();
130 		}
131 	}
132 	leave();
133 }
134 
135 void
clrest(void)136 clrest(void)
137 {
138 	int     r, c, j;
139 
140 	getyx(stdscr, r, c);
141 	for (j = r + 1; j < 24; j++) {
142 		move(j, 0);
143 		clrtoeol();
144 	}
145 	move(r, c);
146 }
147 
148 int
brdeq(const int * b1,const int * b2)149 brdeq(const int *b1, const int *b2)
150 {
151 	const int    *e;
152 
153 	e = b1 + 26;
154 	while (b1 < e)
155 		if (*b1++ != *b2++)
156 			return(0);
157 	return(1);
158 }
159