Mercurial > dropbear
comparison tcpfwd.c @ 4:fe6bca95afa7
Makefile.in contains updated files required
author | Matt Johnston <matt@ucc.asn.au> |
---|---|
date | Tue, 01 Jun 2004 02:46:09 +0000 |
parents | |
children |
comparison
equal
deleted
inserted
replaced
-1:000000000000 | 4:fe6bca95afa7 |
---|---|
1 #include "includes.h" | |
2 #include "tcpfwd.h" | |
3 #include "session.h" | |
4 #include "dbutil.h" | |
5 | |
6 void tcp_fwd_initialise() { | |
7 | |
8 /* just one slot to start with */ | |
9 ses.tcplisteners = | |
10 (struct TCPListener**)m_malloc(sizeof(struct TCPListener*)); | |
11 ses.tcplistensize = 1; | |
12 ses.tcplisteners[0] = NULL; | |
13 | |
14 } | |
15 | |
16 void set_tcp_fwd_fds(fd_set * readfds) { | |
17 | |
18 unsigned int i; | |
19 struct TCPListener *listener; | |
20 | |
21 /* check each in turn */ | |
22 for (i = 0; i < ses.tcplistensize; i++) { | |
23 listener = ses.tcplisteners[i]; | |
24 if (listener != NULL) { | |
25 FD_SET(listener->sock, readfds); | |
26 } | |
27 } | |
28 } | |
29 | |
30 | |
31 void handle_tcp_fwd(fd_set * readfds) { | |
32 | |
33 unsigned int i; | |
34 struct TCPListener *listener; | |
35 | |
36 /* check each in turn */ | |
37 for (i = 0; i < ses.tcplistensize; i++) { | |
38 listener = ses.tcplisteners[i]; | |
39 if (listener != NULL) { | |
40 if (FD_ISSET(listener->sock, readfds)) { | |
41 listener->accepter(listener); | |
42 } | |
43 } | |
44 } | |
45 } | |
46 | |
47 | |
48 /* accepter(int fd, void* typedata) is a function to accept connections, | |
49 * cleanup(void* typedata) happens when cleaning up */ | |
50 int new_fwd(int sock, int type, void* typedata, | |
51 void (*accepter)(struct TCPListener*), | |
52 void (*cleanup)(struct TCPListener*)) { | |
53 | |
54 unsigned int i, j; | |
55 struct TCPListener *newtcp = NULL; | |
56 /* try get a new structure to hold it */ | |
57 for (i = 0; i < ses.tcplistensize; i++) { | |
58 if (ses.tcplisteners[i] == NULL) { | |
59 break; | |
60 } | |
61 } | |
62 | |
63 /* or create a new one */ | |
64 if (i == ses.tcplistensize) { | |
65 if (ses.tcplistensize > MAX_TCPLISTENERS) { | |
66 TRACE(("leave newlistener: too many already")); | |
67 close(sock); | |
68 return DROPBEAR_FAILURE; | |
69 } | |
70 | |
71 ses.tcplisteners = (struct TCPListener**)m_realloc(ses.tcplisteners, | |
72 (ses.tcplistensize+TCP_EXTEND_SIZE) | |
73 *sizeof(struct TCPListener*)); | |
74 | |
75 ses.tcplistensize += TCP_EXTEND_SIZE; | |
76 | |
77 for (j = i; j < ses.tcplistensize; j++) { | |
78 ses.tcplisteners[j] = NULL; | |
79 } | |
80 } | |
81 | |
82 ses.maxfd = MAX(ses.maxfd, sock); | |
83 | |
84 newtcp = (struct TCPListener*)m_malloc(sizeof(struct TCPListener)); | |
85 newtcp->index = i; | |
86 newtcp->type = type; | |
87 newtcp->typedata = typedata; | |
88 newtcp->sock = sock; | |
89 newtcp->accepter = accepter; | |
90 newtcp->cleanup = cleanup; | |
91 | |
92 ses.tcplisteners[i] = newtcp; | |
93 return DROPBEAR_SUCCESS; | |
94 } | |
95 | |
96 /* Return the first listener which matches the type-specific comparison | |
97 * function */ | |
98 struct TCPListener * get_listener(int type, void* typedata, | |
99 int (*match)(void*, void*)) { | |
100 | |
101 unsigned int i; | |
102 struct TCPListener* listener; | |
103 | |
104 for (i = 0, listener = ses.tcplisteners[i]; i < ses.tcplistensize; i++) { | |
105 if (listener->type == type | |
106 && match(typedata, listener->typedata)) { | |
107 return listener; | |
108 } | |
109 } | |
110 | |
111 return NULL; | |
112 } | |
113 | |
114 void remove_listener(struct TCPListener* listener) { | |
115 | |
116 if (listener->cleanup) { | |
117 listener->cleanup(listener); | |
118 } | |
119 | |
120 close(listener->sock); | |
121 ses.tcplisteners[listener->index] = NULL; | |
122 m_free(listener); | |
123 | |
124 } |