summaryrefslogtreecommitdiff
path: root/peer.h
blob: 9eccbe3ed2bf0a6bf8c2445eb3610f4b1054e548 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
/* $Id$ */
/*
 * Copyright (c) 2005 Dimitri Sokolyuk <demon@vhost.dyndns.org>
 *
 * Permission to use, copy, modify, and distribute this software for any
 * purpose with or without fee is hereby granted, provided that the above
 * copyright notice and this permission notice appear in all copies.
 *
 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
 */

#ifndef _PEER_H_
#define _PEER_H_

#if 0
#include <sys/queue.h>
#endif

#if 0
snum stage {
	PIECELESS,	/* threshold 5% */
	NORMAL,
	ENDGAME,	/* threshold 95% */
	SEEDER
};
#endif

enum msg {
	MSG_KEEPALIVE = -1,	/* no payload at all */
	MSG_CHOKE,
	MSG_UNCHOKE,
	MSG_INTERESTED,
	MSG_UNINTERESTED,
	MSG_HAVE,
	MSG_BITFIELD,
	MSG_REQUEST,
	MSG_PIECE,
	MSG_CANCEL
};

/* peer wire message */
struct btpwm {
	u_int	length;
	u_char	id;
	void	*payload;
};

enum state {
	IDLE,
	CONNECTING,
	HANDSHAKE,
	SUCCESS,
	FAILED
};

#define MAX_TTL		10
#define BLOCKSZ		(16<10)

struct btpeerstat {		/* isn't used jet */
	unsigned	int choked:1;
	unsigned	int interested:1;
};

enum flags {
	LOCAL_CHOKED,
	LOCAL_INTERESTED,
	REMOTE_CHOKED,
	REMOTE_INTERESTED,
	OPTIMISTIC_CHOKING
};

struct btpeer {
	LIST_ENTRY(btpeer) link;
#if 1
	int	sockd;
	struct	sockaddr_in sin;
#else
	struct	btsock sock;
#endif
	u_char	peerid[SHA1LEN];	/* isn't known in `compact' mode */
	enum	msg msg;		/* ??? local/remote */
	enum	state state;
	int	ttl;			/* TODO: choose resonable value */
	char	flags;			/* chocked / interested / ... */
	char	*bitfield;		/* alloc space to hold bitfield and
					   data arrays on successful connect */
#if 1	/* obsolete */
	/* request part */
	int	piece;
	off_t	offset;
	size_t	length;
	void	*data_in;		/* holds unfinished parts of piece */
	void	*data_out;
	void	*data;
#endif

	char	*msgbuf;
	size_t	buflen;
	size_t	bufoff;
//	size_t	expect;			/* expect to read */

	/* statistics */
	int	dl;			/* download rate */
	int	ul;			/* upload rate */
	int	rank;
};

/* todo: read first 4 bytes, allocate space in msgbuf, read entry message,
	decide what to do with it */

LIST_HEAD(btplist, btpeer);

__BEGIN_DECLS
char	*btgethandshake(const u_char *, const u_char *);
int	btchkhandshake(const char *, const u_char *, const u_char *);

void	btdumpplist(struct btplist *);
int	btaddpeer(struct btplist *, struct btpeer *);
int	btclearoldpeers(struct btplist *);
void	btdelplist(struct btplist *);
void	btdbg(struct btpeer *, char *, ...);
__END_DECLS

#endif /* not _PEER_H_ */