File:  [ELWIX - Embedded LightWeight unIX -] / embedaddon / php / ext / enchant / enchant.c
Revision 1.1.1.2 (vendor branch): download - view: text, annotated - select for diffs - revision graph
Tue May 29 12:34:37 2012 UTC (12 years, 1 month ago) by misho
Branches: php, MAIN
CVS tags: v5_4_3elwix, v5_4_17p0, HEAD
php 5.4.3+patches

    1: /*
    2:   +----------------------------------------------------------------------+
    3:   | PHP Version 5                                                        |
    4:   +----------------------------------------------------------------------+
    5:   | Copyright (c) 1997-2012 The PHP Group                                |
    6:   +----------------------------------------------------------------------+
    7:   | This source file is subject to version 3.0 of the PHP license,       |
    8:   | that is bundled with this package in the file LICENSE, and is        |
    9:   | available at through the world-wide-web at                           |
   10:   | http://www.php.net/license/3_0.txt.                                  |
   11:   | If you did not receive a copy of the PHP license and are unable to   |
   12:   | obtain it through the world-wide-web, please send a note to          |
   13:   | license@php.net so we can mail you a copy immediately.               |
   14:   +----------------------------------------------------------------------+
   15:   | Author: Pierre-Alain Joye <paj@pearfr.org>                           |
   16:   |         Ilia Alshanetsky <ilia@prohost.org>                          |
   17:   +----------------------------------------------------------------------+
   18: 
   19:   $Id: enchant.c,v 1.1.1.2 2012/05/29 12:34:37 misho Exp $
   20: */
   21: 
   22: #ifdef HAVE_CONFIG_H
   23: #include "config.h"
   24: #endif
   25: 
   26: #include <enchant.h>
   27: #include "php.h"
   28: #include "php_ini.h"
   29: #include "ext/standard/info.h"
   30: #include "php_enchant.h"
   31: 
   32: typedef EnchantBroker * EnchantBrokerPtr;
   33: typedef struct _broker_struct enchant_broker;
   34: typedef struct _dict_struct enchant_dict;
   35: 
   36: typedef enchant_broker * enchant_brokerPtr;
   37: typedef enchant_dict * enchant_dictPtr;
   38: 
   39: typedef struct _broker_struct {
   40: 	EnchantBroker	*pbroker;
   41: 	enchant_dict	**dict;
   42: 	unsigned int	dictcnt;
   43: 	long			rsrc_id;
   44: } _enchant_broker;
   45: 
   46: typedef struct _dict_struct {
   47: 	unsigned int	id;
   48: 	EnchantDict		*pdict;
   49: 	enchant_broker	*pbroker;
   50: 	long			rsrc_id;
   51: 	enchant_dict	*next;
   52: 	enchant_dict	*prev;
   53: } _enchant_dict;
   54: 
   55: 
   56: /* True global resources - no need for thread safety here */
   57: static int le_enchant_broker;
   58: static int le_enchant_dict;
   59: 
   60: /* If you declare any globals in php_enchant.h uncomment this:*/
   61: /*ZEND_DECLARE_MODULE_GLOBALS(enchant)*/
   62: 
   63: #define PHP_ENCHANT_MYSPELL 1
   64: #define PHP_ENCHANT_ISPELL 2
   65: 
   66: /* {{{ arginfo */
   67: ZEND_BEGIN_ARG_INFO(arginfo_enchant_broker_init, 0)
   68: ZEND_END_ARG_INFO()
   69: 
   70: ZEND_BEGIN_ARG_INFO_EX(arginfo_enchant_broker_free, 0, 0, 1)
   71: 	ZEND_ARG_INFO(0, broker)
   72: ZEND_END_ARG_INFO()
   73: 
   74: ZEND_BEGIN_ARG_INFO_EX(arginfo_enchant_broker_set_dict_path, 0, 0, 3)
   75: 	ZEND_ARG_INFO(0, broker)
   76: 	ZEND_ARG_INFO(0, name)
   77: 	ZEND_ARG_INFO(0, value)
   78: ZEND_END_ARG_INFO()
   79: 
   80: ZEND_BEGIN_ARG_INFO_EX(arginfo_enchant_broker_get_dict_path, 0, 0, 2)
   81: 	ZEND_ARG_INFO(0, broker)
   82: 	ZEND_ARG_INFO(0, name)
   83: ZEND_END_ARG_INFO()
   84: 
   85: ZEND_BEGIN_ARG_INFO_EX(arginfo_enchant_broker_request_dict, 0, 0, 2)
   86: 	ZEND_ARG_INFO(0, broker)
   87: 	ZEND_ARG_INFO(0, tag)
   88: ZEND_END_ARG_INFO()
   89: 
   90: ZEND_BEGIN_ARG_INFO_EX(arginfo_enchant_broker_request_pwl_dict, 0, 0, 2)
   91: 	ZEND_ARG_INFO(0, broker)
   92: 	ZEND_ARG_INFO(0, filename)
   93: ZEND_END_ARG_INFO()
   94: 
   95: ZEND_BEGIN_ARG_INFO_EX(arginfo_enchant_broker_free_dict, 0, 0, 1)
   96: 	ZEND_ARG_INFO(0, dict)
   97: ZEND_END_ARG_INFO()
   98: 
   99: ZEND_BEGIN_ARG_INFO_EX(arginfo_enchant_broker_set_ordering, 0, 0, 3)
  100: 	ZEND_ARG_INFO(0, broker)
  101: 	ZEND_ARG_INFO(0, tag)
  102: 	ZEND_ARG_INFO(0, ordering)
  103: ZEND_END_ARG_INFO()
  104: 
  105: ZEND_BEGIN_ARG_INFO_EX(arginfo_enchant_dict_quick_check, 0, 0, 2)
  106: 	ZEND_ARG_INFO(0, dict)
  107: 	ZEND_ARG_INFO(0, word)
  108: 	ZEND_ARG_INFO(1, suggestions)
  109: ZEND_END_ARG_INFO()
  110: 
  111: ZEND_BEGIN_ARG_INFO_EX(arginfo_enchant_dict_check, 0, 0, 2)
  112: 	ZEND_ARG_INFO(0, dict)
  113: 	ZEND_ARG_INFO(0, word)
  114: ZEND_END_ARG_INFO()
  115: 
  116: ZEND_BEGIN_ARG_INFO_EX(arginfo_enchant_dict_store_replacement, 0, 0, 3)
  117: 	ZEND_ARG_INFO(0, dict)
  118: 	ZEND_ARG_INFO(0, mis)
  119: 	ZEND_ARG_INFO(0, cor)
  120: ZEND_END_ARG_INFO()
  121: /* }}} */
  122: 
  123: /* {{{ enchant_functions[]
  124:  *
  125:  * Every user visible function must have an entry in enchant_functions[].
  126:  */
  127: zend_function_entry enchant_functions[] = {
  128: 	PHP_FE(enchant_broker_init, 			arginfo_enchant_broker_init)
  129: 	PHP_FE(enchant_broker_free, 			arginfo_enchant_broker_free)
  130: 	PHP_FE(enchant_broker_get_error, 		arginfo_enchant_broker_free)
  131: 	PHP_FE(enchant_broker_set_dict_path,	arginfo_enchant_broker_set_dict_path)
  132: 	PHP_FE(enchant_broker_get_dict_path,	arginfo_enchant_broker_get_dict_path)
  133: 	PHP_FE(enchant_broker_list_dicts, 		arginfo_enchant_broker_free)
  134: 	PHP_FE(enchant_broker_request_dict,		arginfo_enchant_broker_request_dict)
  135: 	PHP_FE(enchant_broker_request_pwl_dict, arginfo_enchant_broker_request_pwl_dict)
  136: 	PHP_FE(enchant_broker_free_dict, 		arginfo_enchant_broker_free_dict)
  137: 	PHP_FE(enchant_broker_dict_exists, 		arginfo_enchant_broker_request_dict)
  138: 	PHP_FE(enchant_broker_set_ordering, 	arginfo_enchant_broker_set_ordering)
  139: 	PHP_FE(enchant_broker_describe, 		arginfo_enchant_broker_free)
  140: 	PHP_FE(enchant_dict_check, 				arginfo_enchant_dict_check)
  141: 	PHP_FE(enchant_dict_suggest, 			arginfo_enchant_dict_check)
  142: 	PHP_FE(enchant_dict_add_to_personal, 	arginfo_enchant_dict_check)
  143: 	PHP_FE(enchant_dict_add_to_session, 	arginfo_enchant_dict_check)
  144: 	PHP_FE(enchant_dict_is_in_session, 		arginfo_enchant_dict_check)
  145: 	PHP_FE(enchant_dict_store_replacement, 	arginfo_enchant_dict_store_replacement)
  146: 	PHP_FE(enchant_dict_get_error, 			arginfo_enchant_broker_free_dict)
  147: 	PHP_FE(enchant_dict_describe, 			arginfo_enchant_broker_free_dict)
  148: 	PHP_FE(enchant_dict_quick_check, 		arginfo_enchant_dict_quick_check)
  149: 	PHP_FE_END
  150: };
  151: /* }}} */
  152: 
  153: /* {{{ enchant_module_entry
  154:  */
  155: zend_module_entry enchant_module_entry = {
  156: #if ZEND_MODULE_API_NO >= 20010901
  157: 	STANDARD_MODULE_HEADER,
  158: #endif
  159: 	"enchant",
  160: 	enchant_functions,
  161: 	PHP_MINIT(enchant),
  162: 	PHP_MSHUTDOWN(enchant),
  163: 	NULL,	/* Replace with NULL if there's nothing to do at request start */
  164: 	NULL,	/* Replace with NULL if there's nothing to do at request end */
  165: 	PHP_MINFO(enchant),
  166: #if ZEND_MODULE_API_NO >= 20010901
  167: 	PHP_ENCHANT_VERSION,
  168: #endif
  169: 	STANDARD_MODULE_PROPERTIES
  170: };
  171: /* }}} */
  172: 
  173: #ifdef COMPILE_DL_ENCHANT
  174: ZEND_GET_MODULE(enchant)
  175: #endif
  176: 
  177: static void
  178: enumerate_providers_fn (const char * const name,
  179:                         const char * const desc,
  180:                         const char * const file,
  181:                         void * ud) /* {{{ */
  182: {
  183: 	zval *zdesc = (zval *) ud;
  184: 	zval *tmp_array;
  185: 
  186: 	MAKE_STD_ZVAL(tmp_array);
  187: 	array_init(tmp_array);
  188: 
  189: 	add_assoc_string(tmp_array, "name", (char *)name, 1);
  190: 	add_assoc_string(tmp_array, "desc", (char *)desc, 1);
  191: 	add_assoc_string(tmp_array, "file", (char *)file, 1);
  192: 
  193: 	if (Z_TYPE_P(zdesc)!=IS_ARRAY) {
  194: 		array_init(zdesc);
  195: 	}
  196: 
  197: 	add_next_index_zval(zdesc, tmp_array);
  198: }
  199: /* }}} */
  200: 
  201: static void
  202: describe_dict_fn (const char * const lang,
  203:                   const char * const name,
  204:                   const char * const desc,
  205:                   const char * const file,
  206:                   void * ud) /* {{{ */
  207: {
  208: 	zval *zdesc = (zval *) ud;
  209: 	array_init(zdesc);
  210: 	add_assoc_string(zdesc, "lang", (char *)lang, 1);
  211: 	add_assoc_string(zdesc, "name", (char *)name, 1);
  212: 	add_assoc_string(zdesc, "desc", (char *)desc, 1);
  213: 	add_assoc_string(zdesc, "file", (char *)file, 1);
  214: }
  215: /* }}} */
  216: 
  217: static void php_enchant_list_dicts_fn( const char * const lang_tag,
  218: 	   	const char * const provider_name, const char * const provider_desc,
  219: 		const char * const provider_file, void * ud) /* {{{ */
  220: {
  221: 	zval *zdesc = (zval *) ud;
  222: 	zval *tmp_array;
  223: 
  224: 	MAKE_STD_ZVAL(tmp_array);
  225: 	array_init(tmp_array);
  226: 	add_assoc_string(tmp_array, "lang_tag", (char *)lang_tag, 1);
  227: 	add_assoc_string(tmp_array, "provider_name", (char *)provider_name, 1);
  228: 	add_assoc_string(tmp_array, "provider_desc", (char *)provider_desc, 1);
  229: 	add_assoc_string(tmp_array, "provider_file", (char *)provider_file, 1);
  230: 
  231: 	if (Z_TYPE_P(zdesc) != IS_ARRAY) {
  232: 		array_init(zdesc);
  233: 	}
  234: 	add_next_index_zval(zdesc, tmp_array);
  235: 
  236: }
  237: /* }}} */
  238: 
  239: static void php_enchant_broker_free(zend_rsrc_list_entry *rsrc TSRMLS_DC) /* {{{ */
  240: {
  241: 	if (rsrc->ptr) {
  242: 		enchant_broker *broker = (enchant_broker *)rsrc->ptr;
  243: 		if (broker) {
  244: 			if (broker->pbroker) {
  245: 				if (broker->dictcnt && broker->dict) {
  246: 					if (broker->dict) {
  247: 						int total;
  248: 						total = broker->dictcnt-1;
  249: 						do {
  250: 							zend_list_delete(broker->dict[total]->rsrc_id);
  251: 							efree(broker->dict[total]);
  252: 							total--;
  253: 						} while (total>=0);
  254: 					}
  255: 					efree(broker->dict);
  256: 					broker->dict = NULL;
  257: 				}
  258: 				enchant_broker_free(broker->pbroker);
  259: 			}
  260: 			efree(broker);
  261: 		}
  262: 	}
  263: }
  264: /* }}} */
  265: 
  266: static void php_enchant_dict_free(zend_rsrc_list_entry *rsrc TSRMLS_DC) /* {{{ */
  267: 
  268: {
  269: 	if (rsrc->ptr) {
  270: 		enchant_dict *pdict = (enchant_dict *)rsrc->ptr;
  271: 		if (pdict) {
  272: 			if (pdict->pdict && pdict->pbroker) {
  273: 				enchant_broker_free_dict(pdict->pbroker->pbroker, pdict->pdict);
  274: 				if (pdict->id) {
  275: 					pdict->pbroker->dict[pdict->id-1]->next = NULL;
  276: 				}
  277: 				zend_list_delete(pdict->pbroker->rsrc_id);
  278: 			}
  279: 
  280: 		}
  281: 	}
  282: }
  283: /* }}} */
  284: 
  285: /* {{{ PHP_MINIT_FUNCTION
  286:  */
  287: PHP_MINIT_FUNCTION(enchant)
  288: {
  289: 	le_enchant_broker = zend_register_list_destructors_ex(php_enchant_broker_free, NULL, "enchant_broker", module_number);
  290: 	le_enchant_dict = zend_register_list_destructors_ex(php_enchant_dict_free, NULL, "enchant_dict", module_number);
  291: 	REGISTER_LONG_CONSTANT("ENCHANT_MYSPELL", PHP_ENCHANT_MYSPELL, CONST_CS | CONST_PERSISTENT);
  292: 	REGISTER_LONG_CONSTANT("ENCHANT_ISPELL", PHP_ENCHANT_ISPELL, CONST_CS | CONST_PERSISTENT);
  293: 	return SUCCESS;
  294: }
  295: /* }}} */
  296: 
  297: /* {{{ PHP_MSHUTDOWN_FUNCTION
  298:  */
  299: PHP_MSHUTDOWN_FUNCTION(enchant)
  300: {
  301: 	return SUCCESS;
  302: }
  303: /* }}} */
  304: 
  305: static void __enumerate_providers_fn (const char * const name,
  306:                         const char * const desc,
  307:                         const char * const file,
  308:                         void * ud) /* {{{ */
  309: {
  310: 	php_info_print_table_row(3, name, desc, file);
  311: }
  312: /* }}} */
  313: 
  314: /* {{{ PHP_MINFO_FUNCTION
  315:  */
  316: PHP_MINFO_FUNCTION(enchant)
  317: {
  318: 	EnchantBroker *pbroker;
  319: 
  320: 	pbroker = enchant_broker_init();
  321: 	php_info_print_table_start();
  322: 	php_info_print_table_header(2, "enchant support", "enabled");
  323: 	php_info_print_table_row(2, "Version", PHP_ENCHANT_VERSION);
  324: #ifdef ENCHANT_VERSION_STRING
  325: 	php_info_print_table_row(2, "Libenchant Version", ENCHANT_VERSION_STRING);
  326: #elif defined(HAVE_ENCHANT_BROKER_SET_PARAM)
  327: 	php_info_print_table_row(2, "Libenchant Version", "1.5.0 or later");
  328: #endif
  329: 	php_info_print_table_row(2, "Revision", "$Id: enchant.c,v 1.1.1.2 2012/05/29 12:34:37 misho Exp $");
  330: 	php_info_print_table_end();
  331: 
  332: 	php_info_print_table_start();
  333: 	enchant_broker_describe(pbroker, __enumerate_providers_fn, NULL);
  334: 	php_info_print_table_end();
  335: 	enchant_broker_free(pbroker);
  336: }
  337: /* }}} */
  338: 
  339: #define PHP_ENCHANT_GET_BROKER	\
  340: 	ZEND_FETCH_RESOURCE(pbroker, enchant_broker *, &broker, -1, "enchant_broker", le_enchant_broker);	\
  341: 	if (!pbroker || !pbroker->pbroker) {	\
  342: 		php_error_docref(NULL TSRMLS_CC, E_WARNING, "%s", "Resource broker invalid");	\
  343: 		RETURN_FALSE;	\
  344: 	}
  345: 
  346: #define PHP_ENCHANT_GET_DICT	\
  347: 	ZEND_FETCH_RESOURCE(pdict, enchant_dict *, &dict, -1, "enchant_dict", le_enchant_dict);	\
  348: 	if (!pdict || !pdict->pdict) {	\
  349: 		php_error_docref(NULL TSRMLS_CC, E_WARNING, "%s", "Invalid dictionary resource.");	\
  350: 		RETURN_FALSE;	\
  351: 	}
  352: 
  353: /* {{{ proto resource enchant_broker_init()
  354:    create a new broker object capable of requesting */
  355: PHP_FUNCTION(enchant_broker_init)
  356: {
  357: 	enchant_broker *broker;
  358: 	EnchantBroker *pbroker;
  359: 
  360: 	if (zend_parse_parameters_none() == FAILURE) {
  361: 		return;
  362: 	}
  363: 
  364: 	pbroker = enchant_broker_init();
  365: 
  366: 	if (pbroker) {
  367: 		broker = (enchant_broker *) emalloc(sizeof(enchant_broker));
  368: 		broker->pbroker = pbroker;
  369: 		broker->dict = NULL;
  370: 		broker->dictcnt = 0;
  371: 		broker->rsrc_id = ZEND_REGISTER_RESOURCE(return_value, broker, le_enchant_broker);
  372: 	} else {
  373: 		RETURN_FALSE;
  374: 	}
  375: }
  376: /* }}} */
  377: 
  378: /* {{{ proto boolean enchant_broker_free(resource broker)
  379:    Destroys the broker object and its dictionnaries */
  380: PHP_FUNCTION(enchant_broker_free)
  381: {
  382: 	zval *broker;
  383: 	enchant_broker *pbroker;
  384: 
  385: 	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "r", &broker) == FAILURE) {
  386: 		RETURN_FALSE;
  387: 	}
  388: 	PHP_ENCHANT_GET_BROKER;
  389: 
  390: 	zend_list_delete(Z_RESVAL_P(broker));
  391: 	RETURN_TRUE;
  392: }
  393: /* }}} */
  394: 
  395: /* {{{ proto string enchant_broker_get_error(resource broker)
  396:    Returns the last error of the broker */
  397: PHP_FUNCTION(enchant_broker_get_error)
  398: {
  399: 	zval *broker;
  400: 	enchant_broker *pbroker;
  401: 	char *msg;
  402: 
  403: 	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "r", &broker) == FAILURE) {
  404: 		RETURN_FALSE;
  405: 	}
  406: 
  407: 	PHP_ENCHANT_GET_BROKER;
  408: 
  409: 	msg = enchant_broker_get_error(pbroker->pbroker);
  410: 	if (msg) {
  411: 		RETURN_STRING((char *)msg, 1);
  412: 	}
  413: 	RETURN_FALSE;
  414: }
  415: /* }}} */
  416: 
  417: #if HAVE_ENCHANT_BROKER_SET_PARAM
  418: /* {{{ proto bool enchant_broker_set_dict_path(resource broker, int dict_type, string value)
  419: 	Set the directory path for a given backend, works with ispell and myspell */
  420: PHP_FUNCTION(enchant_broker_set_dict_path)
  421: {
  422: 	zval *broker;
  423: 	enchant_broker *pbroker;
  424: 	long dict_type;
  425: 	char *value;
  426: 	int value_len;
  427: 
  428: 	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rls", &broker, &dict_type, &value, &value_len) == FAILURE) {
  429: 		RETURN_FALSE;
  430: 	}
  431: 
  432: 	if (!value_len) {
  433: 		RETURN_FALSE;
  434: 	}
  435: 	
  436: 	PHP_ENCHANT_GET_BROKER;
  437: 
  438: 	switch (dict_type) {
  439: 		case PHP_ENCHANT_MYSPELL:
  440: 			PHP_ENCHANT_GET_BROKER;
  441: 			enchant_broker_set_param(pbroker->pbroker, "enchant.myspell.dictionary.path", (const char *)value);
  442: 			RETURN_TRUE;
  443: 			break;
  444: 
  445: 		case PHP_ENCHANT_ISPELL:
  446: 			PHP_ENCHANT_GET_BROKER;
  447: 			enchant_broker_set_param(pbroker->pbroker, "enchant.ispell.dictionary.path", (const char *)value);
  448: 			RETURN_TRUE;
  449: 			break;
  450: 
  451: 		default:
  452: 			RETURN_FALSE;
  453: 	}
  454: }
  455: /* }}} */
  456: 
  457: 
  458: /* {{{ proto string enchant_broker_get_dict_path(resource broker, int dict_type)
  459: 	Get the directory path for a given backend, works with ispell and myspell */
  460: PHP_FUNCTION(enchant_broker_get_dict_path)
  461: {
  462: 	zval *broker;
  463: 	enchant_broker *pbroker;
  464: 	long dict_type;
  465: 	char *value;
  466: 
  467: 	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rl", &broker, &dict_type) == FAILURE) {
  468: 		RETURN_FALSE;
  469: 	}
  470: 	
  471: 	PHP_ENCHANT_GET_BROKER;
  472: 
  473: 	switch (dict_type) {
  474: 		case PHP_ENCHANT_MYSPELL:
  475: 			PHP_ENCHANT_GET_BROKER;
  476: 			value = enchant_broker_get_param(pbroker->pbroker, "enchant.myspell.dictionary.path");
  477: 			break;
  478: 
  479: 		case PHP_ENCHANT_ISPELL:
  480: 			PHP_ENCHANT_GET_BROKER;
  481: 			value = enchant_broker_get_param(pbroker->pbroker, "enchant.ispell.dictionary.path");
  482: 			break;
  483: 
  484: 		default:
  485: 			RETURN_FALSE;
  486: 	}
  487: 
  488: 	RETURN_STRING(value, 1);
  489: }
  490: /* }}} */
  491: #else
  492: /* {{{ proto bool enchant_broker_set_dict_path(resource broker, int dict_type, string value)
  493: 	Set the directory path for a given backend, works with ispell and myspell */
  494: PHP_FUNCTION(enchant_broker_set_dict_path)
  495: {
  496: 	RETURN_FALSE;
  497: }
  498: /* }}} */
  499: 
  500: 
  501: /* {{{ proto string enchant_broker_get_dict_path(resource broker, int dict_type)
  502: 	Get the directory path for a given backend, works with ispell and myspell */
  503: PHP_FUNCTION(enchant_broker_get_dict_path)
  504: {
  505: 	RETURN_FALSE;
  506: }
  507: /* }}} */
  508: #endif
  509: 
  510: /* {{{ proto string enchant_broker_list_dicts(resource broker)
  511:    Lists the dictionaries available for the given broker */
  512: PHP_FUNCTION(enchant_broker_list_dicts)
  513: {
  514: 	zval *broker;
  515: 	enchant_broker *pbroker;
  516: 
  517: 	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "r", &broker) == FAILURE) {
  518: 		RETURN_FALSE;
  519: 	}
  520: 
  521: 	PHP_ENCHANT_GET_BROKER;
  522: 
  523: 	enchant_broker_list_dicts(pbroker->pbroker, php_enchant_list_dicts_fn, (void *)return_value);
  524: }
  525: /* }}} */
  526: 
  527: /* {{{ proto resource enchant_broker_request_dict(resource broker, string tag)
  528: 	create a new dictionary using tag, the non-empty language tag you wish to request
  529: 	a dictionary for ("en_US", "de_DE", ...) */
  530: PHP_FUNCTION(enchant_broker_request_dict)
  531: {
  532: 	zval *broker;
  533: 	enchant_broker *pbroker;
  534: 	enchant_dict *dict;
  535: 	EnchantDict *d;
  536: 	char *tag;
  537: 	int taglen;
  538: 	int pos;
  539: 
  540: 	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rs", &broker, &tag, &taglen) == FAILURE) {
  541: 		RETURN_FALSE;
  542: 	}
  543: 
  544: 	PHP_ENCHANT_GET_BROKER;
  545: 	
  546: 	if (taglen == 0) {
  547: 		php_error_docref(NULL TSRMLS_CC, E_WARNING, "Tag cannot be empty");
  548: 		RETURN_FALSE;
  549: 	}
  550: 
  551: 	d = enchant_broker_request_dict(pbroker->pbroker, (const char *)tag);
  552: 	if (d) {
  553: 		if (pbroker->dictcnt) {
  554: 			pbroker->dict = (enchant_dict **)erealloc(pbroker->dict, sizeof(enchant_dict *) * pbroker->dictcnt);
  555: 			pos = pbroker->dictcnt++;
  556: 		} else {
  557: 			pbroker->dict = (enchant_dict **)emalloc(sizeof(enchant_dict *));
  558: 			pos = 0;
  559: 			pbroker->dictcnt++;
  560: 		}
  561: 
  562: 		dict = pbroker->dict[pos] = (enchant_dict *)emalloc(sizeof(enchant_dict));
  563: 		dict->id = pos;
  564: 		dict->pbroker = pbroker;
  565: 		dict->pdict = d;
  566: 		dict->prev = pos ? pbroker->dict[pos-1] : NULL;
  567: 		dict->next = NULL;
  568: 		pbroker->dict[pos] = dict;
  569: 
  570: 		if (pos) {
  571: 			pbroker->dict[pos-1]->next = dict;
  572: 		}
  573: 
  574: 		dict->rsrc_id = ZEND_REGISTER_RESOURCE(return_value, dict, le_enchant_dict);
  575: 		zend_list_addref(pbroker->rsrc_id);
  576: 	} else {
  577: 		RETURN_FALSE;
  578: 	}
  579: }
  580: /* }}} */
  581: 
  582: /* {{{ proto resource enchant_broker_request_pwl_dict(resource broker, string filename)
  583:    creates a dictionary using a PWL file. A PWL file is personal word file one word per line. It must exist before the call.*/
  584: PHP_FUNCTION(enchant_broker_request_pwl_dict)
  585: {
  586: 	zval *broker;
  587: 	enchant_broker *pbroker;
  588: 	enchant_dict *dict;
  589: 	EnchantDict *d;
  590: 	char *pwl;
  591: 	int pwllen;
  592: 	int pos;
  593: 
  594: 	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rp", &broker, &pwl, &pwllen) == FAILURE) {
  595: 		RETURN_FALSE;
  596: 	}
  597: 
  598: #if PHP_API_VERSION < 20100412
  599: 	if ((PG(safe_mode) && (!php_checkuid(pwl, NULL, CHECKUID_CHECK_FILE_AND_DIR))) || php_check_open_basedir(pwl TSRMLS_CC)) {
  600: #else
  601: 	if (php_check_open_basedir(pwl TSRMLS_CC)) {
  602: #endif
  603: 		RETURN_FALSE;
  604: 	}
  605: 
  606: 	PHP_ENCHANT_GET_BROKER;
  607: 
  608: 	d = enchant_broker_request_pwl_dict(pbroker->pbroker, (const char *)pwl);
  609: 	if (d) {
  610: 		if (pbroker->dictcnt) {
  611: 			pos = pbroker->dictcnt++;
  612: 			pbroker->dict = (enchant_dict **)erealloc(pbroker->dict, sizeof(enchant_dict *) * pbroker->dictcnt);
  613: 		} else {
  614: 			pbroker->dict = (enchant_dict **)emalloc(sizeof(enchant_dict *));
  615: 			pos = 0;
  616: 			pbroker->dictcnt++;
  617: 		}
  618: 		dict = pbroker->dict[pos] = (enchant_dict *)emalloc(sizeof(enchant_dict));
  619: 		dict->id = pos;
  620: 		dict->pbroker = pbroker;
  621: 		dict->pdict = d;
  622: 		dict->prev = pos?pbroker->dict[pos-1]:NULL;
  623: 		dict->next = NULL;
  624: 		pbroker->dict[pos] = dict;
  625: 		if (pos) {
  626: 			pbroker->dict[pos-1]->next = dict;
  627: 		}
  628: 		dict->rsrc_id = ZEND_REGISTER_RESOURCE(return_value, dict, le_enchant_dict);
  629: 	} else {
  630: 		RETURN_FALSE;
  631: 	}
  632: }
  633: /* }}} */
  634: 
  635: /* {{{ proto resource enchant_broker_free_dict(resource dict)
  636:    Free the dictionary resource */
  637: PHP_FUNCTION(enchant_broker_free_dict)
  638: {
  639: 	zval *dict;
  640: 	enchant_dict *pdict;
  641: 
  642: 	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "r", &dict) == FAILURE) {
  643: 		RETURN_FALSE;
  644: 	}
  645: 
  646: 	PHP_ENCHANT_GET_DICT;
  647: 
  648: 	zend_list_delete(Z_RESVAL_P(dict));
  649: 	RETURN_TRUE;
  650: }
  651: /* }}} */
  652: 
  653: /* {{{ proto bool enchant_broker_dict_exists(resource broker, string tag)
  654:    Wether a dictionary exists or not. Using non-empty tag */
  655: PHP_FUNCTION(enchant_broker_dict_exists)
  656: {
  657: 	zval *broker;
  658: 	char *tag;
  659: 	int taglen;
  660: 	enchant_broker * pbroker;
  661: 
  662: 	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rs", &broker, &tag, &taglen) == FAILURE) {
  663: 		RETURN_FALSE;
  664: 	}
  665: 
  666: 	PHP_ENCHANT_GET_BROKER;
  667: 
  668: 	RETURN_BOOL(enchant_broker_dict_exists(pbroker->pbroker, tag));
  669: }
  670: /* }}} */
  671: 
  672: /* {{{ proto bool enchant_broker_set_ordering(resource broker, string tag, string ordering)
  673: 	Declares a preference of dictionaries to use for the language
  674: 	described/referred to by 'tag'. The ordering is a comma delimited
  675: 	list of provider names. As a special exception, the "*" tag can
  676: 	be used as a language tag to declare a default ordering for any
  677: 	language that does not explictly declare an ordering. */
  678: 
  679: PHP_FUNCTION(enchant_broker_set_ordering)
  680: {
  681: 	zval *broker;
  682: 	char *pordering;
  683: 	int porderinglen;
  684: 	char *ptag;
  685: 	int ptaglen;
  686: 	enchant_broker * pbroker;
  687: 
  688: 	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rss", &broker, &ptag, &ptaglen, &pordering, &porderinglen) == FAILURE) {
  689: 		RETURN_FALSE;
  690: 	}
  691: 
  692: 	PHP_ENCHANT_GET_BROKER;
  693: 
  694: 	enchant_broker_set_ordering(pbroker->pbroker, ptag, pordering);
  695: 	RETURN_TRUE;
  696: }
  697: /* }}} */
  698: 
  699: /* {{{ proto array enchant_broker_describe(resource broker)
  700: 	Enumerates the Enchant providers and tells you some rudimentary information about them. The same info is provided through phpinfo() */
  701: PHP_FUNCTION(enchant_broker_describe)
  702: {
  703: 	EnchantBrokerDescribeFn describetozval = enumerate_providers_fn;
  704: 	zval *broker;
  705: 	enchant_broker * pbroker;
  706: 
  707: 	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "r", &broker) == FAILURE) {
  708: 		RETURN_FALSE;
  709: 	}
  710: 
  711: 	PHP_ENCHANT_GET_BROKER;
  712: 
  713: 	enchant_broker_describe(pbroker->pbroker, describetozval, (void *)return_value);
  714: }
  715: /* }}} */
  716: 
  717: /* {{{ proto bool enchant_dict_quick_check(resource dict, string word [, array &suggestions])
  718:     If the word is correctly spelled return true, otherwise return false, if suggestions variable
  719:     is provided, fill it with spelling alternatives. */
  720: PHP_FUNCTION(enchant_dict_quick_check)
  721: {
  722: 	zval *dict, *sugg = NULL;
  723: 	char *word;
  724: 	int wordlen;
  725: 	enchant_dict *pdict;
  726: 
  727: 	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rs|z/", &dict, &word, &wordlen, &sugg) == FAILURE) {
  728: 		RETURN_FALSE;
  729: 	}
  730: 
  731: 	if (sugg) {
  732: 		zval_dtor(sugg);
  733: 	}
  734: 
  735: 	PHP_ENCHANT_GET_DICT;
  736: 
  737: 	if (enchant_dict_check(pdict->pdict, word, wordlen) > 0) {
  738: 		int n_sugg;
  739: 		size_t n_sugg_st;
  740: 		char **suggs;
  741: 
  742: 		if (!sugg && ZEND_NUM_ARGS() == 2) {
  743: 			RETURN_FALSE;
  744: 		}
  745: 
  746: 		array_init(sugg);
  747: 
  748: 		suggs = enchant_dict_suggest(pdict->pdict, word, wordlen, &n_sugg_st);
  749: 		memcpy(&n_sugg, &n_sugg_st, sizeof(n_sugg));
  750: 		if (suggs && n_sugg) {
  751: 			int i;
  752: 			for (i = 0; i < n_sugg; i++) {
  753: 				add_next_index_string(sugg, suggs[i], 1);
  754: 			}
  755: 			enchant_dict_free_suggestions(pdict->pdict, suggs);
  756: 		}
  757: 
  758: 
  759: 		RETURN_FALSE;
  760: 	}
  761: 	RETURN_TRUE;
  762: }
  763: /* }}} */
  764: 
  765: /* {{{ proto bool enchant_dict_check(resource dict, string word)
  766:     If the word is correctly spelled return true, otherwise return false */
  767: PHP_FUNCTION(enchant_dict_check)
  768: {
  769: 	zval *dict;
  770: 	char *word;
  771: 	int wordlen;
  772: 	enchant_dict *pdict;
  773: 
  774: 	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rs", &dict, &word, &wordlen) == FAILURE) {
  775: 		RETURN_FALSE;
  776: 	}
  777: 
  778: 	PHP_ENCHANT_GET_DICT;
  779: 
  780: 	RETURN_BOOL(!enchant_dict_check(pdict->pdict, word, wordlen));
  781: }
  782: /* }}} */
  783: 
  784: /* {{{ proto array enchant_dict_suggest(resource dict, string word)
  785:     Will return a list of values if any of those pre-conditions are not met.*/
  786: PHP_FUNCTION(enchant_dict_suggest)
  787: {
  788: 	zval *dict;
  789: 	char *word;
  790: 	int wordlen;
  791: 	char **suggs;
  792: 	enchant_dict *pdict;
  793: 	int n_sugg;
  794: 	size_t n_sugg_st;
  795: 
  796: 	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rs", &dict, &word, &wordlen) == FAILURE) {
  797: 		RETURN_FALSE;
  798: 	}
  799: 
  800: 	PHP_ENCHANT_GET_DICT;
  801: 
  802: 	suggs = enchant_dict_suggest(pdict->pdict, word, wordlen, &n_sugg_st);
  803: 	memcpy(&n_sugg, &n_sugg_st, sizeof(n_sugg));
  804: 	if (suggs && n_sugg) {
  805: 		int i;
  806: 
  807: 		array_init(return_value);
  808: 		for (i = 0; i < n_sugg; i++) {
  809: 			add_next_index_string(return_value, suggs[i], 1);
  810: 		}
  811: 
  812: 		enchant_dict_free_suggestions(pdict->pdict, suggs);
  813: 	}
  814: }
  815: /* }}} */
  816: 
  817: /* {{{ proto void enchant_dict_add_to_personal(resource dict, string word)
  818:      add 'word' to personal word list */
  819: PHP_FUNCTION(enchant_dict_add_to_personal)
  820: {
  821: 	zval *dict;
  822: 	char *word;
  823: 	int wordlen;
  824: 	enchant_dict *pdict;
  825: 
  826: 	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rs", &dict, &word, &wordlen) == FAILURE) {
  827: 		RETURN_FALSE;
  828: 	}
  829: 
  830: 	PHP_ENCHANT_GET_DICT;
  831: 
  832: 	enchant_dict_add_to_personal(pdict->pdict, word, wordlen);
  833: }
  834: /* }}} */
  835: 
  836: /* {{{ proto void enchant_dict_add_to_session(resource dict, string word)
  837:    add 'word' to this spell-checking session */
  838: PHP_FUNCTION(enchant_dict_add_to_session)
  839: {
  840: 	zval *dict;
  841: 	char *word;
  842: 	int wordlen;
  843: 	enchant_dict *pdict;
  844: 
  845: 	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rs", &dict, &word, &wordlen) == FAILURE) {
  846: 		RETURN_FALSE;
  847: 	}
  848: 
  849: 	PHP_ENCHANT_GET_DICT;
  850: 
  851: 	enchant_dict_add_to_session(pdict->pdict, word, wordlen);
  852: }
  853: /* }}} */
  854: 
  855: /* {{{ proto bool enchant_dict_is_in_session(resource dict, string word)
  856:    whether or not 'word' exists in this spelling-session */
  857: PHP_FUNCTION(enchant_dict_is_in_session)
  858: {
  859: 	zval *dict;
  860: 	char *word;
  861: 	int wordlen;
  862: 	enchant_dict *pdict;
  863: 
  864: 	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rs", &dict, &word, &wordlen) == FAILURE) {
  865: 		RETURN_FALSE;
  866: 	}
  867: 
  868: 	PHP_ENCHANT_GET_DICT;
  869: 
  870: 	RETURN_BOOL(enchant_dict_is_in_session(pdict->pdict, word, wordlen));
  871: }
  872: /* }}} */
  873: 
  874: /* {{{ proto void enchant_dict_store_replacement(resource dict, string mis, string cor)
  875: 	add a correction for 'mis' using 'cor'.
  876: 	Notes that you replaced @mis with @cor, so it's possibly more likely
  877: 	that future occurrences of @mis will be replaced with @cor. So it might
  878: 	bump @cor up in the suggestion list.*/
  879: PHP_FUNCTION(enchant_dict_store_replacement)
  880: {
  881: 	zval *dict;
  882: 	char *mis, *cor;
  883: 	int mislen, corlen;
  884: 
  885: 	enchant_dict *pdict;
  886: 
  887: 	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rss", &dict, &mis, &mislen, &cor, &corlen) == FAILURE) {
  888: 		RETURN_FALSE;
  889: 	}
  890: 
  891: 	PHP_ENCHANT_GET_DICT;
  892: 
  893: 	enchant_dict_store_replacement(pdict->pdict, mis, mislen, cor, corlen);
  894: }
  895: /* }}} */
  896: 
  897: /* {{{ proto string enchant_dict_get_error(resource dict)
  898:    Returns the last error of the current spelling-session */
  899: PHP_FUNCTION(enchant_dict_get_error)
  900: {
  901: 	zval *dict;
  902: 	enchant_dict *pdict;
  903: 	char *msg;
  904: 
  905: 	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "r", &dict) == FAILURE) {
  906: 		RETURN_FALSE;
  907: 	}
  908: 
  909: 	PHP_ENCHANT_GET_DICT;
  910: 
  911: 	msg = enchant_dict_get_error(pdict->pdict);
  912: 	if (msg) {
  913: 		RETURN_STRING((char *)msg, 1);
  914: 	}
  915: 
  916: 	RETURN_FALSE;
  917: }
  918: /* }}} */
  919: 
  920: /* {{{ proto array enchant_dict_describe(resource dict)
  921:    Describes an individual dictionary 'dict' */
  922: PHP_FUNCTION(enchant_dict_describe)
  923: {
  924: 	zval *dict;
  925: 	enchant_dict *pdict;
  926: 
  927: 	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "r", &dict) == FAILURE) {
  928: 		RETURN_FALSE;
  929: 	}
  930: 
  931: 	PHP_ENCHANT_GET_DICT;
  932: 
  933: 	enchant_dict_describe(pdict->pdict, describe_dict_fn, (void *)return_value);
  934: }
  935: /* }}} */
  936: 
  937: /*
  938:  * Local variables:
  939:  * tab-width: 4
  940:  * c-basic-offset: 4
  941:  * End:
  942:  * vim600: noet sw=4 ts=4 fdm=marker
  943:  * vim<600: noet sw=4 ts=4
  944:  */

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>