-------------
The open proxy monitor library provides an API interface to an open proxy
-scanner. File descriptor and memory allocation are handled internally by calls
-to API functions aswell as the main IO loop (opm_cycle). Configuration, callback
-registry and protocol types are all on a scanner based level. This provides means
-to create multiple 'virtual scanners', each with it's own configuration, limits
-and protocols.
+ scanner. File descriptor and memory allocation are handled internally by
+ calls to API functions as well as the main IO loop (opm_cycle).
+ Configuration, callback registry and protocol types are all on a scanner
+ based level. This provides means to create multiple 'virtual scanners',
+ each with its own configuration, limits and protocols.
+
+
2.0 API Data Types
------------------
OPM_T
- This type holds information regarding a 'virtual scanner'. It is the highest
- type created to proxy scan.
+ This type holds information regarding a 'virtual scanner'. It is the
+ highest-level type created to proxy scan.
OPM_REMOTE_T
- This structure holds information regarding a remote host. An OPM_REMOTE_T must
- be created for each host libopm will scan. The OPM_REMOTE_T struct will be passed
- back on callbacks, so that the client will be able to determine the IP, port and
- protocol in question.
+ This structure holds information regarding a remote host. An OPM_REMOTE_T
+ must be created for each host libopm will scan. The OPM_REMOTE_T struct
+ will be passed back on callbacks, so that the client will be able to
+ determine the IP, port and protocol in question.
- The OPM_REMOTE_T structure is defined in opm.h and is as follows:
+ The OPM_REMOTE_T structure is defined in opm.h and is as follows:
struct OPM_REMOTE_T {
char *ip;
unsigned short int port;
- unsigned short int protocol;
+ const char *protocol;
unsigned short int bytes_read;
OPM_PROTOCOL_T *protocols;
element is handled internally by the API.
data
- An arbitrary pointer used if the client program wants to store additional
- data in the remote struct. This can be used to avoid having to have a seperate
- list of scans outside of the library.
+ An arbitrary pointer used if the client program wants to store
+ additional data in the remote struct. This can be used to avoid
+ having to have a seperate list of scans outside of the library.
+
+
+
2.1 C API Functions
-------------------
Parameters: None
Return: Pointer to OPM_T
- The opm_create function is used to create a new scanner object. Memory for the object
- will be created internally and can be freed with the opm_free function.
+ The opm_create function is used to create a new scanner object. Memory for
+ the object will be created internally and can be freed with the opm_free
+ function.
Parameters: Pointer to OPM_T object to free
Return: None
- The opm_free struct will free a scanner object. All configuration and scans the scanner
- is engaged in will be destroyed.
-
+ The opm_free struct will free a scanner object. All configuration and scans
+ the scanner is engaged in will be destroyed.
OPM_REMOTE_T *opm_remote_create(char *)
- Parameters: Pointer to string containing human readable IP address of remote host
+ Parameters: Pointer to string containing presentation-format IPv4 address
+ of remote host
Return: Pointer to OPM_REMOTE_T
- The opm_remote_create function will allocate and setup a OPM_REMOTE_T object which
- contains information on a remote host being scanned. OPM_REMOTE_T objects are passed
- to the scanner to initiate scanning, and then are passed back on events.
-
+ The opm_remote_create function will allocate and setup a OPM_REMOTE_T
+ object which contains information on a remote host being scanned.
+ OPM_REMOTE_T objects are passed to the scanner to initiate scanning, and
+ then are passed back on events.
The opm_remote_free function frees up an OPM_REMOTE_T struct.
- WARNING: Freeing an OPM_REMOTE_T struct after it has been passed to
- a scanner (via opm_scan) would give unpredictable results.
+ WARNING: Freeing an OPM_REMOTE_T struct after it has been passed to a
+ scanner (via opm_scan) would give unpredictable results.
- It is only safe to free an OPM_REMOTE_T struct after the end scan
- callback has been called.
+ It is only safe to free an OPM_REMOTE_T struct after the end scan
+ callback has been called.
+
OPM_ERR_BADKEY: The key (configuration option) is unknown.
OPM_ERR_UNKNOWN: Unknown error.
- The opm_config function sets various options on the individual scanner
- objects. A pointer to the data to set the option to is required. The scanner
- will make a copy of the data and store it internally.
+ The opm_config function sets various options on the individual scanner
+ objects. A pointer to the data to set the option to is required. The
+ scanner will make a copy of the data and store it internally.
Configuration Types
- OPTION TYPE DESCRIPTION
- --------------------------------------------------------------------------
+ OPTION TYPE DESCRIPTION
+ ---------------------------------------------------------------------
- fd_limit int Max file descriptor limit
+ fd_limit int Max file descriptor limit
- bind_ip char * IP to bind to for outgoing scans
+ bind_ip char * IP to bind to for outgoing scans
- target_string list of char * Target strings used to verify open proxies
+ target_string list of char * Target strings used to verify open
+ proxies
- scan_ip char * IP to command proxies to connect to
+ scan_ip char * IP to command proxies to connect to
- scan_port int port to command proxies to connect to
+ scan_port int port to command proxies to connect to
- max_read int Maximum amount of data (in bytes) to be read from
- the remote connection until it is dropped.
+ max_read int Maximum amount of data (in bytes) to be
+ read from the remote connection until
+ it is dropped.
- timeout int Time in seconds before a negotiation is considered
- timed out, and closed.
+ timeout int Time in seconds before a negotiation is
+ considered timed out, and closed.
- dnsbl_host char * DNSBL host
+ dnsbl_host char * DNSBL host
should be called after opm_create.
-
-OPM_ERR_T opm_addtype(OPM_T *, int, int)
-OPM_ERR_T opm_remote_addtype(OPM_REMOTE_T *, int, int)
+
+
+OPM_ERR_T opm_protocol_add(const char *, OPM_CALLBACK_T, OPM_CALLBACK_T)
+
+ Parameters: const char *: Type (name) of this protocol
+ OPM_PROXYWRITE_T *: Protocol's write function
+ OPM_PROXYREAD_T *: Protocol's read function
+
+ Return: OPM_ERR_T or OPM_SUCCESS on success
+
+ OPM_ERR_DUPEPROTO: Protocol is already registered.
+ OPM_RR_UNKNOWN: Unknown error.
+
+ The opm_protocol_add function is used to register a new protocol with
+ libopm. This function is normally used to add support for thrird-party
+ protocols not supplied with libopm. The following protocols are supplied
+ with libopm:
+
+ Protocol Description
+ ---------------------------------------------------------------------
+ HTTP HTTP CONNECT
+ WINGATE Insecure WinGate proxy
+ ROUTER Misconfigured or default password router (often Cisco)
+ SOCKS4 SOCKS v4
+ SOCKS5 SOCKS v5
+
+ The above protocols are registered by opm_create. Once a protocol is
+ registered, it is available to all scanners.
+
+
+
+
+OPM_ERR_T opm_addtype(OPM_T *, const char *, int)
+OPM_ERR_T opm_remote_addtype(OPM_REMOTE_T *, const char *, int)
Parameters: OPM_T scanner to add type to
- int: type to add
+ const char *: type to add
int: port of type to add
Return: OPM_ERR_T or OPM_SUCCESS on success
The opm_addtype function adds a protocol type and port to the scanner's
protocol list. This list determines what ports the scanner will scan on,
- and what protocols it will check for on those ports. Each protocol/port will
- result in 1 file descriptor used per scan.
+ and what protocols it will check for on those ports. Each protocol/port
+ will result in 1 file descriptor used per scan.
The opm_remote_addtype functions works similarly, but adds the protocol
configuration to an individual remote struct instead.
+ Protocols supported by default by libopm:
- Type Description
+ Type Description
---------------------------------------------------------------------
- OPM_TYPE_HTTP Open http proxies
- OPM_TYPE_SOCKS4 Open socks 4 proxies
- OPM_TYPE_SOCKS5 Open socks 5 proxies
- OPM_TYPE_ROUTER Routers with default passwords set (usually cisco)
- OPM_TYPE_WINGATE Open wingate proxy
- OPM_TYPE_POST Opm HTTP post proxy
+ HTTP Open HTTP CONNECT proxies
+ SOCKS4 Open SOCKS 4 proxies
+ SOCKS5 Open SOCKS 5 proxies
+ ROUTER Routers with default passwords set (usually cisco)
+ WINGATE Open wingate proxy
+ HTTPPOST Opm HTTP POST proxy
Example:
OPM_T *scanner;
scanner = opm_create();
- opm_addtype(scanner, OPM_TYPE_HTTP, 80);
- opm_addtype(scanner, OPM_TYPE_HTTP, 8080);
- opm_addtype(scanner, OPM_TYPE_HTTP, 3128);
- opm_addtype(scanner, OPM_TYPE_SOCKS4, 1080);
- opm_addtype(scanner, OPM_TYPE_SOCKS5, 1080);
- opm_addtype(scanner, OPM_TYPE_ROUTER, 23);
- opm_addtype(scanner, OPM_TYPE_WINGATE, 23);
- opm_addtype(scanner, OPM_TYPE_POST, 80);
+ opm_addtype(scanner, "HTTP", 80);
+ opm_addtype(scanner, "HTTP", 8080);
+ opm_addtype(scanner, "HTTP", 3128);
+ opm_addtype(scanner, "SOCKS4", 1080);
+ opm_addtype(scanner, "SOCKS5", 1080);
+ opm_addtype(scanner, "ROUTER", 23);
+ opm_addtype(scanner, "WINGATE", 23);
+ opm_addtype(scanner, "HTTPPOST", 80);
opm_free(scanner);
+
+
OPM_ERR_T opm_scan(OPM_T *, OPM_REMOTE_T *)
Parameters: OPM_T: Scanner to scan on
- OPM_REMOTE_T: Object containing information on remote host to scan
+ OPM_REMOTE_T: Object containing information on remote host to
+ scan
Return: OPM_ERR_T or OPM_SUCCESS on success
OPM_ERR_BADADDR: The address within the OPM_REMOTE_T is not valid.
OPM_ERR_NOPROTOCOLS: No protocols are configured.
- The opm_scan functions adds a remote host object to the scanner's scan queue
- (or begins scanning on it if there is no queue).
+ The opm_scan functions adds a remote host object to the scanner's scan
+ queue (or begins scanning on it if there is no queue).
Example:
scanner = opm_create();
remote_host = opm_remote_create("10.0.0.1");
- opm_addtype(scanner, OPM_TYPE_HTTP, 80);
+ opm_addtype(scanner, "HTTP", 80);
opm_scan(scanner, remote_host);
+
void opm_end(OPM_T *, OPM_REMOTE_T *)
void opm_endscan(OPM_T *, OPM_REMOTE_T *)
when the scans end
The opm_end function ends all scans using the passed OPM_REMOTE_T. The
- opm_endscan will only end active scans (scans in the queue are not
+ opm_endscan will only end active scans (scans in the queue are not
traversed). This is useful if it is known only one scan using the remote
struct exists, but it is also known that the scan has already active.
Using opm_endscan will save time by not traversing the queue list.
IMPORTANT: If the opm_end function ends any scans in the queue, the
- OPM_CALLBACK_END callback will be called immadiately for
- those scans. Any scans in the active scan list will be set
- OPM_STATE_CLOSED and OPM_CALLBACK_END for those scans will
- be called on the next opm_cycle.
+ OPM_CALLBACK_END callback will be called immadiately for those
+ scans. Any scans in the active scan list will be set
+ OPM_STATE_CLOSED and OPM_CALLBACK_END for those scans will be
+ called on the next opm_cycle.
+
+
OPM_ERR_T opm_callback(OPM_T *, int, OPM_CALLBACK_T, void *)
Parameters: OPM_T: Scanner to set callbacks on
for events. The opm_remote_callback can be used to set remote host specific
callback functions.
- The first parameter to the callback function is the scanner in question, the
- second is the remote host object in question, and the third is an optional integer
- used for error codes.
+ The first parameter to the callback function is the scanner in question,
+ the second is the callback type.
- The the OPENPROXY, NEGFAIL, TIMEOUT, and ERROR functions, the OPM_REMOTE struct
- will have OPM_REMOTE_T::protocol, OPM_REMOTE_T::port and OPM_REMOTE_T::bytes_read
- set.
+ For callbacks of type OPENPROXY, NEGFAIL, TIMEOUT, and ERROR, the
+ OPM_REMOTE struct will have OPM_REMOTE_T::protocol, OPM_REMOTE_T::port and
+ OPM_REMOTE_T::bytes_read set.
- Type Description
+ Type Description
--------------------------------------------------------------------------------
- OPM_CALLBACK_OPENPROXY An open proxy has been found.
-
- OPM_CALLBACK_NEGFAIL Negotiation with the remote end has failed.
+ OPM_CALLBACK_OPENPROXY An open proxy has been found.
- OPM_CALLBACK_TIMEOUT Neogitation with the remote end has timed out
+ OPM_CALLBACK_NEGFAIL Negotiation with the remote end has failed.
- OPM_CALLBACK_END Scan on remote host is complete, the OPM_REMOTE_T
- has been removed from the scanner and is safe to
- opm_remote_free
+ OPM_CALLBACK_TIMEOUT Negotiation with the remote end has timed out.
- OPM_CALLBACK_ERROR An error has occured.
+ OPM_CALLBACK_END Scan on remote host is complete, the OPM_REMOTE_T
+ has been removed from the scanner and is safe to
+ opm_remote_free.
+ OPM_CALLBACK_ERROR An error has occured.
opm_cycle passes one cycle to a scanner. During a cycle the following functions
are performed in order:
- 1. Scans are moved from a queue list to a live scan list if OPM_CONFIG_FD_LIMIT has not
- yet been reached.
+ 1. Scans are moved from a queue list to a live scan list if
+ OPM_CONFIG_FD_LIMIT has not yet been reached.
- 2. Scans in the live scan list are 'established'. That is, if OPM_CONFIG_FD_LIMIT has not
- yet been reached, new connections will be established until OPM_CONFIG_FD_LIMIT is reached
- or all scans have active file descriptors.
+ 2. Scans in the live scan list are 'established'. That is, if
+ OPM_CONFIG_FD_LIMIT has not yet been reached, new connections will
+ be established until OPM_CONFIG_FD_LIMIT is reached or all scans
+ have active file descriptors.
- 3. All scans are polled for read, write and negotiation failed events. Upon write event,
- negotiation related data is sent to the remote host to negotiate the open proxy. Upon
- read event, data is read in and tested against target strings. Upon negotiation fail (HUP)
- events, scans are marked closed.
+ 3. All scans are polled for read, write and negotiation failed events.
+ Upon write event, negotiation related data is sent to the remote
+ host to negotiate the open proxy. Upon read event, data is read in
+ and tested against target strings. Upon negotiation fail (HUP)
+ events, scans are marked closed.
- 4. Free up the file descriptors of connections marked closed and remove such connections
- from the scan list. If no connections are left for a given remote host, consider the scan
- on that host ended and remove it from the scanner.
+ 4. Free up the file descriptors of connections marked closed and
+ remove such connections from the scan list. If no connections are
+ left for a given remote host, consider the scan on that host ended
+ and remove it from the scanner.
- opm_cycle will need to be called consistently within the main loop of the client application.
- opm_cycle will not block or cause delays. It is up to the client application to rate calls to
- opm_cycle in order to save CPU.
+ opm_cycle will need to be called consistently within the main loop of the
+ client application. opm_cycle will not block or cause delays. It is up to
+ the client application to rate calls to opm_cycle in order to save CPU.
-/* vim: set shiftwidth=3 softtabstop=3 expandtab: */
+/* vim: set shiftwidth=3 softtabstop=3 cinoptions=(0 expandtab: */
/*
* Copyright (C) 2002-2003 Erik Fears
# include <string.h>
#endif
+#include <stdio.h>
+
RCSID("$Id$");
static OPM_PROTOCOL_CONFIG_T *libopm_protocol_config_create(void);
*
*/
-static OPM_PROTOCOL_T OPM_PROTOCOLS[] = {
- {OPM_TYPE_HTTP, libopm_proxy_http_write, NULL},
- {OPM_TYPE_SOCKS4, libopm_proxy_socks4_write, NULL},
- {OPM_TYPE_SOCKS5, libopm_proxy_socks5_write, NULL},
- {OPM_TYPE_ROUTER, libopm_proxy_router_write, NULL},
- {OPM_TYPE_WINGATE, libopm_proxy_wingate_write, NULL},
- {OPM_TYPE_HTTPPOST, libopm_proxy_httppost_write, NULL},
- {OPM_TYPE_HTTPGET, libopm_proxy_httpget_write, NULL},
- {OPM_TYPE_MINDJAIL, libopm_trojan_mindjail_write, libopm_trojan_mindjail_read},
-};
+/* List of protocols registered. */
+OPM_LIST_T *OPM_PROTOCOLS = NULL;
/* opm_create
ret->protocols = libopm_list_create();
ret->fd_use = 0;
+ /* Setup protocols. */
+ OPM_PROTOCOLS = libopm_list_create();
+ libopm_protocol_add("HTTP", libopm_proxy_http_write, NULL);
+ libopm_protocol_add("SOCKS4", libopm_proxy_socks4_write, NULL);
+ libopm_protocol_add("SOCKS5", libopm_proxy_socks5_write, NULL);
+ libopm_protocol_add("ROUTER", libopm_proxy_router_write, NULL);
+ libopm_protocol_add("WINGATE", libopm_proxy_wingate_write, NULL);
+ libopm_protocol_add("HTTPPOST", libopm_proxy_httppost_write, NULL);
+ libopm_protocol_add("HTTPGET", libopm_proxy_httpget_write, NULL);
+ libopm_protocol_add("MINDJAIL", libopm_trojan_mindjail_write, NULL);
+
+
/* Setup callbacks */
ret->callbacks = MyMalloc(sizeof(OPM_CALLBACK_T) * LIBOPM_CBLEN);
OPM_NODE_T *p, *next;
OPM_PROTOCOL_CONFIG_T *ppc;
OPM_SCAN_T *scan;
+ OPM_PROTOCOL_T *pp;
libopm_config_free(scanner->config);
MyFree(scanner->callbacks);
MyFree(scanner);
+
+ LIST_FOREACH_SAFE(p, next, OPM_PROTOCOLS->head)
+ {
+ pp = p->data;
+ MyFree(pp->type);
+ libopm_list_remove(OPM_PROTOCOLS, p);
+ libopm_node_free(p);
+ }
+
+ libopm_list_free(OPM_PROTOCOLS);
}
* type: type of data the key holds
*
* Return:
- * OPM_ERR_T contianing error code (or OPM_SUCCESS)
+ * OPM_ERR_T containing error code (or OPM_SUCCESS)
*/
OPM_ERR_T opm_config_add(OPM_T *scanner, const char *key, int type)
+/*
+ * libopm_protocol_add
+ *
+ * Register a new protocol with libopm.
+ *
+ * Parameters:
+ * type: Type (name) of the protocol
+ * write: Protocol's write function
+ * read: Protocol's read function
+ *
+ * Return:
+ * OPM_ERR_T containing error code (or OPM_SUCCESS)
+ */
+OPM_ERR_T libopm_protocol_add(const char *type, OPM_PROXYWRITE_T *write,
+ OPM_PROXYREAD_T *read)
+{
+ OPM_NODE_T *p;
+ OPM_PROTOCOL_T *pp;
+
+ LIST_FOREACH(p, OPM_PROTOCOLS->head)
+ {
+ pp = p->data;
+
+ if(strcmp(type, pp->type) == 0)
+ return OPM_ERR_DUPEPROTO;
+ }
+
+ pp = MyMalloc(sizeof *pp);
+ pp->type = strdup(type);
+ pp->write_function = write;
+ pp->read_function = read;
+ p = libopm_node_create(pp);
+ libopm_list_add(OPM_PROTOCOLS, p);
+
+ return OPM_SUCCESS;
+}
+
+
+
/* opm_addtype
*
* OPM_ERR_BADPROTOCOL: Protocol is unknown
*/
-OPM_ERR_T opm_addtype(OPM_T *scanner, int type, unsigned short int port)
+OPM_ERR_T opm_addtype(OPM_T *scanner, const char *type,
+ unsigned short int port)
{
- unsigned int i;
-
- OPM_NODE_T *node;
+ OPM_NODE_T *node, *p;
OPM_PROTOCOL_CONFIG_T *protocol_config;
+ OPM_PROTOCOL_T *pp;
- for(i = 0; i < sizeof(OPM_PROTOCOLS) / sizeof(OPM_PROTOCOL_T); i++)
+ LIST_FOREACH(p, OPM_PROTOCOLS->head)
{
- if(type == OPM_PROTOCOLS[i].type)
+ pp = p->data;
+
+ if(strcmp(type, pp->type) == 0)
{
protocol_config = libopm_protocol_config_create();
- protocol_config->type = &OPM_PROTOCOLS[i];
+ protocol_config->type = pp;
protocol_config->port = port;
-
+
node = libopm_node_create(protocol_config);
libopm_list_add(scanner->protocols, node);
* OPM_ERR_BADPROTOCOL: Protocol is unknown
*/
-OPM_ERR_T opm_remote_addtype(OPM_REMOTE_T *remote, int type, unsigned short int port)
+OPM_ERR_T opm_remote_addtype(OPM_REMOTE_T *remote, const char *type,
+ unsigned short int port)
{
- unsigned int i;
-
- OPM_NODE_T *node;
+ OPM_NODE_T *node, *p;
OPM_PROTOCOL_CONFIG_T *protocol_config;
+ OPM_PROTOCOL_T *pp;
- for(i = 0; i < sizeof(OPM_PROTOCOLS) / sizeof(OPM_PROTOCOL_T); i++)
+ LIST_FOREACH(p, OPM_PROTOCOLS->head)
{
- if(type == OPM_PROTOCOLS[i].type)
+ pp = p->data;
+
+ if(strcmp(type, pp->type) == 0)
{
protocol_config = libopm_protocol_config_create();
- protocol_config->type = &OPM_PROTOCOLS[i];
+ protocol_config->type = pp;
protocol_config->port = port;
node = libopm_node_create(protocol_config);
return OPM_SUCCESS;
}
}
- return OPM_ERR_BADPROTOCOL;
-}
-
-
-
-/* libopm_protocol_create
- *
- * Create OPM_PROTOCOL_T struct.
- *
- * Parameters:
- * None
- * Return:
- * Pointer to new struct
- *
- * XXX - does not appear to be used anywhere?
- * -grifferz
- */
-
-#if 0
-static OPM_PROTOCOL_T *libopm_protocol_create(void)
-{
- OPM_PROTOCOL_T *ret;
- ret = MyMalloc(sizeof(OPM_PROTOCOL_T));
-
- ret->type = 0;
- ret->write_function = NULL;
- ret->read_function = NULL;
-
- return ret;
+ return OPM_ERR_BADPROTOCOL;
}
-#endif
-
-
-/* libopm_protocol_free
- *
- * Free an OPM_PROTOCOL_T struct. Assume that if
- * format is not NULL, it is pointed to dynamically
- * allocated memory and free it.
- *
- * Parameters:
- * protocol: struct to free
- *
- * Return:
- * None
- *
- * XXX - apparently no longer used?
- * -grifferz
- */
-#if 0
-static void libopm_protocol_free(OPM_PROTOCOL_T *protocol)
-{
- MyFree(protocol);
-}
-#endif
+/* vim: set shiftwidth=3 softtabstop=3 cinoptions=(0 expandtab: */
+
#ifndef LIBOPM_H
#define LIBOPM_H
#include "opm_common.h"
#include "opm.h"
-#define LIBOPM_CBLEN 5 /* Number of callback functions */
-#define LIBOPM_READBUFLEN 128 /* Size of conn->readbuf */
-#define LIBOPM_SENDBUFLEN 512 /* Size of sendbuffer in proxy.c */
+/* Number of callback functions. */
+#define LIBOPM_CBLEN 5
+/* Size of conn->readbuf. */
+#define LIBOPM_READBUFLEN 128
+/* Size of sendbuffer in proxy.c. */
+#define LIBOPM_SENDBUFLEN 512
typedef struct _OPM_SCAN OPM_SCAN_T;
typedef struct _OPM_CONNECTION OPM_CONNECTION_T;
typedef struct _OPM_PROTOCOL_CONFIG OPM_PROTOCOL_CONFIG_T;
typedef struct _OPM_PROTOCOL OPM_PROTOCOL_T;
-/* Types of hard coded proxy READ/WRITE functions which are
- setup in a table in libopm.c */
-
+/*
+ * Types of hard-coded proxy READ/WRITE functions which are
+ * set up in a table in libopm.c.
+ */
typedef int OPM_PROXYWRITE_T (OPM_T *, OPM_SCAN_T *, OPM_CONNECTION_T *);
typedef int OPM_PROXYREAD_T (OPM_T *, OPM_SCAN_T *, OPM_CONNECTION_T *);
struct _OPM_SCAN {
- opm_sockaddr addr; /* Address in byte order of remote
- client */
- OPM_REMOTE_T *remote; /* Pointed to the OPM_REMOTE_T for
- this scan, passed by client */
- OPM_LIST_T *connections; /* List of individual connections
- of this scan (1 for each protocol) */
+ /* Address in byte order of remote client. */
+ opm_sockaddr addr;
+ /* Pointer to the OPM_REMOTE_T for this scan, passed by client. */
+ OPM_REMOTE_T *remote;
+ /* List of individual connections of this scan (1 for each protocol). */
+ OPM_LIST_T *connections;
};
struct _OPM_CONNECTION {
-
- OPM_PROTOCOL_T *protocol; /* Pointer to specific protocol
- this connection handles */
- unsigned short int port; /* Some protocols have multiple
- ports, eg. HTTP */
-
- int fd; /* Allocated file descriptor, 0 if
- not yet allocated */
- unsigned short int bytes_read; /* Bytes read so far in this
- connection */
- char readbuf[LIBOPM_READBUFLEN + 1];
- /* 128 byte read buffer, anything
- over 128 is probably not of use */
- unsigned short int readlen; /* Length of readbuf */
- unsigned short int state; /* State of connection */
- unsigned char flags;
- time_t creation; /* When this connection was
- established */
- void *data; /* Arbitrary protocol-specific data */
+ /* Pointer to specific protocol this connection handles. */
+ OPM_PROTOCOL_T *protocol;
+ /* Proxies have a port as well as a protocol. */
+ unsigned short int port;
+
+ /* Allocated file descriptor, 0 if not yet allocated. */
+ int fd;
+ /* Bytes read so far in this connection. */
+ unsigned short int bytes_read;
+ /* 128 byte read buffer, anything over 128 is probably not of use. */
+ char readbuf[LIBOPM_READBUFLEN + 1];
+ /* Length of readbuf. */
+ unsigned short int readlen;
+ /* State of connection. */
+ unsigned short int state;
+ unsigned char flags;
+ /* When this connection was established. */
+ time_t creation;
+ /* Arbitrary protocol-specific data. */
+ void *data;
};
struct _OPM_PROTOCOL_CONFIG
{
- OPM_PROTOCOL_T *type; /* Protocol type */
- unsigned short int port; /* Port to connect on */
+ /* Protocol type. */
+ OPM_PROTOCOL_T *type;
+ /* Port to connect on. */
+ unsigned short int port;
};
struct _OPM_PROTOCOL
{
- int type; /* Protocol type */
+ /* Protocol type. */
+ const char *type;
- OPM_PROXYWRITE_T *write_function; /* Write function handler for this
- protocol */
- OPM_PROXYREAD_T *read_function; /* Read function handler for this
- protocol */
+ /* Write function handler for this protocol. */
+ OPM_PROXYWRITE_T *write_function;
+ /* Read function handler for this protocol. */
+ OPM_PROXYREAD_T *read_function;
};
void libopm_do_callback(OPM_T *, OPM_REMOTE_T *, int, int);
OPM_REMOTE_T *libopm_setup_remote(OPM_REMOTE_T *, OPM_CONNECTION_T *);
void libopm_do_openproxy(OPM_T *, OPM_SCAN_T *, OPM_CONNECTION_T *);
+OPM_ERR_T libopm_protocol_add(const char *, OPM_PROXYWRITE_T *,
+ OPM_PROXYREAD_T *);
#endif /* LIBOPM_H */
-/* vim: set shiftwidth=3 softtabstop=3 expandtab: */
+/* vim: set shiftwidth=3 softtabstop=3 cinoptions=(0 expandtab: */
/** \file opm.h
* \brief Main header for libopm.
char *ip;
/* Port passed back on certain callbacks. */
- unsigned short int port;
+ unsigned short int port;
/* Protocol passed back on certain callbacks. */
- unsigned short int protocol;
+ const char *protocol;
/* Bytes read passed back on certain callbacks. */
unsigned short int bytes_read;
void opm_end(OPM_T *, OPM_REMOTE_T *);
void opm_endscan(OPM_T *, OPM_REMOTE_T *);
-OPM_ERR_T opm_addtype(OPM_T *, int, unsigned short int);
-OPM_ERR_T opm_remote_addtype(OPM_REMOTE_T *, int, unsigned short int);
+OPM_ERR_T opm_addtype(OPM_T *, const char *, unsigned short int);
+OPM_ERR_T opm_remote_addtype(OPM_REMOTE_T *, const char *,
+ unsigned short int);
OPM_ERR_T opm_callback(OPM_T *, int, OPM_CALLBACK_FUNC *, void *);
void opm_cycle(OPM_T *);
+/* vim: set shiftwidth=3 softtabstop=3 cinoptions=(0 expandtab: */
+
#ifndef LIBOPM_ERROR_H
#define LIBOPM_ERROR_H
#define OPM_ERR_BIND 11 /* Error binding to BIND_IP */
#define OPM_ERR_NOFD 12 /* Unable to allocate file descriptor */
+/* Protocol registration errors. */
+#define OPM_ERR_DUPEPROTO 13 /* Attermpt to register duplicate
+ protocol */
+
/* other errors */
-#define OPM_ERR_UNKNOWN 13 /* Unknown error */
+#define OPM_ERR_UNKNOWN 14 /* Unknown error */
#endif /* LIBOPM_ERROR_H */
+/* vim: set shiftwidth=3 softtabstop=3 cinoptions=(0 expandtab: */
+
#ifndef OPM_TYPES_H
#define OPM_TYPES_H
#define OPM_TYPE_ADDRESS 3
#define OPM_TYPE_STRINGLIST 4
-/* Protocols */
-#define OPM_TYPE_HTTP 1
-#define OPM_TYPE_SOCKS4 2
-#define OPM_TYPE_SOCKS5 3
-#define OPM_TYPE_WINGATE 4
-#define OPM_TYPE_ROUTER 5
-#define OPM_TYPE_HTTPPOST 6
-#define OPM_TYPE_HTTPGET 7
-#define OPM_TYPE_MINDJAIL 8
-
/* States */
#define OPM_STATE_UNESTABLISHED 1
#define OPM_STATE_ESTABLISHED 2
+/* vim: set shiftwidth=3 softtabstop=3 cinoptions=(0 expandtab: */
+
/*
* Copyright (C) 2002 Erik Fears
*
* 59 Temple Place - Suite 330
* Boston, MA 02111-1307, USA.
*
- *
*/
#include "setup.h"
/* Setup the protocol configuration */
for (s = ARRAY_SIZEOF(http_ports), i = 0; i < s; i++) {
- opm_addtype(scanner, OPM_TYPE_HTTP, http_ports[i]);
+ opm_addtype(scanner, "HTTP", http_ports[i]);
}
for (s = ARRAY_SIZEOF(wingate_ports), i = 0; i < s; i++) {
- opm_addtype(scanner, OPM_TYPE_WINGATE, wingate_ports[i]);
+ opm_addtype(scanner, "WINGATE", wingate_ports[i]);
}
for (s = ARRAY_SIZEOF(router_ports), i = 0; i < s; i++) {
- opm_addtype(scanner, OPM_TYPE_ROUTER, router_ports[i]);
+ opm_addtype(scanner, "ROUTER", router_ports[i]);
}
for (s = ARRAY_SIZEOF(socks4_ports), i = 0; i < s; i++) {
- opm_addtype(scanner, OPM_TYPE_SOCKS4, socks4_ports[i]);
+ opm_addtype(scanner, "SOCKS4", socks4_ports[i]);
}
for (s = ARRAY_SIZEOF(socks5_ports), i = 0; i < s; i++) {
- opm_addtype(scanner, OPM_TYPE_SOCKS5, socks5_ports[i]);
+ opm_addtype(scanner, "SOCKS5", socks5_ports[i]);
}
for (s = ARRAY_SIZEOF(httppost_ports), i = 0; i < s; i++) {
- opm_addtype(scanner, OPM_TYPE_HTTPPOST, httppost_ports[i]);
+ opm_addtype(scanner, "HTTPPOST", httppost_ports[i]);
}
/* Remote structs can also have their own extended protocol configurations. For instance
if the target hostname contains strings such as 'proxy' or 'www', extended ports could
be scanned. */
- opm_remote_addtype(remote, OPM_TYPE_HTTP, 8001);
- opm_remote_addtype(remote, OPM_TYPE_HTTP, 8002);
+ opm_remote_addtype(remote, "HTTP", 8001);
+ opm_remote_addtype(remote, "HTTP", 8002);
switch(err = opm_scan(scanner, remote))
{
case OPM_SUCCESS:
- break;
+ break;
+
case OPM_ERR_BADADDR:
- printf("Bad address\n");
- opm_free(scanner);
- opm_remote_free(remote);
- return 0;
+ printf("Bad address\n");
+ opm_free(scanner);
+ opm_remote_free(remote);
+ return 0;
+
default:
- printf("Unknown Error %d\n", err);
- return 0;
+ printf("Unknown Error %d\n", err);
+ return 0;
}
-
while(!complete)
opm_cycle(scanner);
}
void open_proxy(OPM_T *scanner, OPM_REMOTE_T *remote, int notused,
- void *data)
+ void *data)
{
USE_VAR(notused);
USE_VAR(data);
- printf("Open proxy on %s:%d [%d bytes read]\n", remote->ip,
- remote->port, remote->bytes_read);
+ printf("Open proxy on %s:%d (%s) [%d bytes read]\n", remote->ip,
+ remote->port, remote->protocol, remote->bytes_read);
opm_end(scanner, remote);
}
void negotiation_failed(OPM_T *scanner, OPM_REMOTE_T *remote, int notused,
- void *data)
+ void *data)
{
USE_VAR(scanner);
USE_VAR(notused);
USE_VAR(data);
printf("Negotiation on %s:%d failed [%d bytes read]\n", remote->ip,
- remote->port, remote->bytes_read);
+ remote->port, remote->bytes_read);
}
void timeout(OPM_T *scanner, OPM_REMOTE_T *remote, int notused, void *data)
case OPM_ERR_MAX_READ:
printf("Reached MAX READ on %s:%d\n", remote->ip, remote->port);
break;
+
case OPM_ERR_BIND:
printf("Unable to bind for %s:%d\n", remote->ip, remote->port);
break;
+
case OPM_ERR_NOFD:
printf("Unable to allocate file descriptor for %s:%d\n",
- remote->ip, remote->port);
+ remote->ip, remote->port);
break;
+
default:
printf("Unknown error on %s:%d, err = %d\n", remote->ip,
- remote->port, err);
+ remote->port, err);
}
}