/* ** $Id: inet.cc,v 1.39 2001/04/26 16:38:41 ch Exp $ ** ** This library was put into the Public Domain by ** Christian Hammers <ch@westend.com>. ** ** string = ewu_ntoa(int); <- inet_ntoa() ** int = ewu_aton(string); <- inet_aton() ** ** I couldn't use inet_ntoa as these names are equal to those from the libc I use ** inside my functions. I guess it's possible when using native mysql functions ** instead of these "udf" functions. ** ** To test use the following two selects: ** select ewu_ntoa(ewu_aton(substring_index("111.112.113.114/15","/",1))); ** select ewu_ntoa(ewu_aton(substring_index("1.2.3.4/5","/",1))); ** SELECT concat(ewu_ntoa(net),'/',mask) as netz FROM netflow_accounting_nets left join kunden using (k_nr) order by kurzname; ** select *,ewu_aton(c.c),ewu_ntoa(a.d) from a left join c using (a) ; ** +------+---------+------+------+---------+---------------+---------------+ ** | a | c | d | a | c | ewu_aton(c.c) | ewu_ntoa(a.d) | ** +------+---------+------+------+---------+---------------+---------------+ ** | 1 | 1.2.3.4 | 181 | 1 | 0.0.0.1 | 1 | 0.0.0.181 | ** | 2 | 2.2.3.4 | 1500 | 2 | 0.0.2.0 | 512 | 0.0.5.220 | ** | 3 | 2.2.3.4 | 624 | 3 | NULL | NULL | 0.0.2.112 | ** | 4 | 4.2.3.4 | NULL | NULL | NULL | NULL | NULL | ** +------+---------+------+------+---------+---------------+---------------+ ** 4 rows in set (0.01 sec) ** ** Changelog: ** 2001-04-26, ch ** Added more fixes to make it real stable with NULL values. ** 2001-04-04, ch ** Rewrote with printf/scanf as I don't get it right with those ** inet_aton/inet_ntoa functions. ** 2001-02-07, ch ** Uploaded to http://empyrean.lib.ndsu.nodak.edu/~nem/mysql/udf/. ** Great site! ** 2001-02-07, ch ** Monty told me that I could not assume that STRING_RESULT ** arguments are null terminated. For this reason there is ** the length field. ** 2001-01-22, ch ** Initial Release. ** ** *******original***docs***below**!!!******************************************* ** ** create function <function_name> returns {string|real|integer} ** soname <name_of_shared_library> ** drop function <function_name> ** ** Each defined function may have a xxxx_init function and a xxxx_deinit ** function. The init function should alloc memory for the function ** and tell the main function about the max length of the result ** (for string functions), number of decimals (for double functions) and ** if the result may be a null value. ** ** If a function sets the 'error' argument to 1 the function will not be ** called anymore and mysqld will return NULL for all calls to this copy ** of the function. ** ** All strings arguments to functions are given as string pointer + length ** to allow handling of binary data. ** Remember that all functions must be thread safe. This means that one is not ** allowed to alloc any global or static variables that changes! ** If one needs memory one should alloc this in the init function and free ** this on the __deinit function. ** ** ... ** ** A dynamicly loadable file should be compiled sharable ** (something like: gcc -shared -o udf_example.so myfunc.cc). ** ... ** The resulting library (udf_example.so) should be copied to some dir ** searched by ld. (/usr/lib ?) ** */
#ifdef STANDARD #include <stdio.h> #else #include <my_global.h> #include <my_sys.h> #endif #include <string.h> #include <mysql.h> #include <m_ctype.h>
#ifdef HAVE_DLOPEN
/* ** CREATE FUNCTION ewu_ntoa RETURNS STRING SONAME "westend_mysql_inet.so"; ** CREATE FUNCTION ewu_aton RETURNS INT SONAME "westend_mysql_inet.so"; */ #include <sys/socket.h> #include <netinet/in.h> #include <arpa/inet.h> #include <netdb.h>
extern "C" { my_bool ewu_ntoa_init(UDF_INIT *initid, UDF_ARGS *args, char *message); void ewu_ntoa_deinit(UDF_INIT *initid); char *ewu_ntoa( UDF_INIT *initid, UDF_ARGS *args, char *result, unsigned long *length, char *null_value, char *error ); }
my_bool ewu_ntoa_init(UDF_INIT *initid, UDF_ARGS *args, char *message) { if (args->arg_count != 1 || args->arg_type[0] != INT_RESULT) { strcpy(message,"Usage: ewu_ntoa(1241152) # like inet_ntoa(3)"); return 1; } initid->maybe_null=0; initid->max_length=15+1; return 0; }
void ewu_ntoa_deinit(UDF_INIT *initid) { }
char *ewu_ntoa(UDF_INIT *initid, UDF_ARGS *args, char *result, unsigned long *res_length, char *is_null, char *error) { if (args->args[0] == NULL || args->lengths[0] < 0 || args->lengths[0] > 0xffffffff) { *is_null=1; *error=1; return 0; } sprintf(result,"%lu.%lu.%lu.%lu", (*((unsigned long int*)(args->args[0])) & 0xff000000) >> 24, (*((unsigned long int*)(args->args[0])) & 0x00ff0000) >> 16, (*((unsigned long int*)(args->args[0])) & 0x0000ff00) >> 8, (*((unsigned long int*)(args->args[0])) & 0x000000ff) >> 0); *res_length = strlen(result); *is_null = 0; *error = 0; return result; }
extern "C" { my_bool ewu_aton_init(UDF_INIT *initid, UDF_ARGS *args, char *message); void ewu_aton_deinit(UDF_INIT *initid); longlong ewu_aton(UDF_INIT *initid, UDF_ARGS *args, char *is_null, char *error); }
my_bool ewu_aton_init(UDF_INIT *initid, UDF_ARGS *args, char *message) { if (args->arg_count != 1 || args->arg_type[0] != STRING_RESULT) { strcpy(message,"Usage: ewu_aton(\"212.117.67.2\") # like inet_aton(3)"); return 1; }
initid->maybe_null=0; return 0; }
void ewu_aton_deinit(UDF_INIT *initid) { }
long long ewu_aton(UDF_INIT *initid, UDF_ARGS *args, char *is_null,char *error) { unsigned long long int a,b,c,d;
if (args->args[0] == NULL || args->lengths[0] < 1 || args->lengths[0] > 15) { *is_null=1; *error=1; return 0; } if (sscanf(args->args[0], "%llu.%llu.%llu.%llu", &a, &b, &c, &d) != 4) { *is_null=1; *error=1; return 0; } if (a>255 || b>255 || c>255 || d>255) { *is_null=1; *error=1; return 0; }
*is_null=0; *error=0; return (unsigned long long int)( a*0x01000000 + b*0x00010000 + c*0x00000100 + d); }
#endif /* HAVE_DLOPEN */
|