4
* Copyright © 2003 Keith Packard
6
* Permission to use, copy, modify, distribute, and sell this software and its
7
* documentation for any purpose is hereby granted without fee, provided that
8
* the above copyright notice appear in all copies and that both that
9
* copyright notice and this permission notice appear in supporting
10
* documentation, and that the name of Keith Packard not be used in
11
* advertising or publicity pertaining to distribution of the software without
12
* specific, written prior permission. Keith Packard makes no
13
* representations about the suitability of this software for any purpose. It
14
* is provided "as is" without express or implied warranty.
16
* KEITH PACKARD DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
17
* INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
18
* EVENT SHALL KEITH PACKARD BE LIABLE FOR ANY SPECIAL, INDIRECT OR
19
* CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
20
* DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
21
* TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
22
* PERFORMANCE OF THIS SOFTWARE.
30
extend namespace Server {
31
public namespace Clients {
32
(&Client)[0] clients = {};
34
public void iterate (void (&Client c) f) {
35
Array::iterate (&clients, f);
38
public exception no_such_client (file f);
40
public void client_send (&Client c, string fmt, poly args...) {
41
RR::Send::send (c.f, fmt, args...);
45
public void server_send (string fmt, poly args...) {
46
void message_client (&Client o) {
48
client_send (&o, fmt, args...);
49
} catch File::io_error (string msg,
50
File::error_type error,
52
File::fprintf (stderr, "%v: %s\n",
57
Clients::iterate (message_client);
60
public &Client select (file f) {
61
exception found (&Client c);
63
void pick (&Client c) {
68
} catch found (&Client c) {
71
raise no_such_client (f);
74
public ClientRef find (string name) {
75
exception found (&Client c);
77
void pick (&Client c) {
78
if (c.user == (User.username) name)
82
} catch found (&Client c) {
83
return (ClientRef.client) (&c);
85
return ClientRef.none;
88
public &Client new (file f) {
89
return Array::append (&clients,
96
return &clients[dim(clients)-1];
99
public void dispose (&Client c) {
100
if (c.user != User.none) {
101
File::fprintf (stderr, "Client disconnect %s\n", c.user.username);
102
Clients::server_send ("NOTICE QUIT %s\n", c.user.username);
104
File::fprintf (stderr, "Client disconnect <unnamed client>\n");
105
Array::remove (&clients, &c);
108
} catch File::io_error (string msg,
109
File::error_type error,
111
File::fprintf (stderr, "%v: %s\n",
116
public void print (&Client c) {
117
File::fprintf (stderr, "%v\n", c);
120
public void print_client (&Client c, &Client o) {
121
union switch (o.user) {
125
client_send (&c, " %s", u);
130
public void print_client_score (&Client c, &Client o) {
131
union switch (o.user) {
135
client_send (&c, " %s %d", u, o.score);
140
public void print_client_games (&Client c, &Client o) {
141
union switch (o.user) {
145
client_send (&c, " %s %d", u, o.games);