numericstring.c 9.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301
  1. /** BEGIN COPYRIGHT BLOCK
  2. * Copyright (C) 2001 Sun Microsystems, Inc. Used by permission.
  3. * Copyright (C) 2009 Red Hat, Inc.
  4. * All rights reserved.
  5. *
  6. * License: GPL (version 3 or any later version).
  7. * See LICENSE for details.
  8. * END COPYRIGHT BLOCK **/
  9. #ifdef HAVE_CONFIG_H
  10. # include <config.h>
  11. #endif
  12. /* numericstring.c - Numeric String syntax routines */
  13. #include <stdio.h>
  14. #include <string.h>
  15. #include <sys/types.h>
  16. #include "syntax.h"
  17. static int numstr_filter_ava( Slapi_PBlock *pb, struct berval *bvfilter,
  18. Slapi_Value **bvals, int ftype, Slapi_Value **retVal );
  19. static int numstr_filter_sub( Slapi_PBlock *pb, char *initial, char **any,
  20. char *final, Slapi_Value **bvals );
  21. static int numstr_values2keys( Slapi_PBlock *pb, Slapi_Value **val,
  22. Slapi_Value ***ivals, int ftype );
  23. static int numstr_assertion2keys( Slapi_PBlock *pb, Slapi_Value *val,
  24. Slapi_Value ***ivals, int ftype );
  25. static int numstr_assertion2keys_sub( Slapi_PBlock *pb, char *initial, char **any,
  26. char *final, Slapi_Value ***ivals );
  27. static int numstr_compare(struct berval *v1, struct berval *v2);
  28. static int numstr_validate(struct berval *val);
  29. static void numstr_normalize(
  30. Slapi_PBlock *pb,
  31. char *s,
  32. int trim_spaces,
  33. char **alt
  34. );
  35. /* the first name is the official one from RFC 4517 */
  36. static char *names[] = { "Numeric String", "numstr", NUMERICSTRING_SYNTAX_OID, 0 };
  37. #define NUMERICSTRINGMATCH_OID "2.5.13.8"
  38. #define NUMERICSTRINGORDERINGMATCH_OID "2.5.13.9"
  39. #define NUMERICSTRINGSUBSTRINGSMATCH_OID "2.5.13.10"
  40. static Slapi_PluginDesc pdesc = { "numstr-syntax", VENDOR,
  41. DS_PACKAGE_VERSION, "numeric string attribute syntax plugin" };
  42. static const char *numericStringMatch_names[] = {"numericStringMatch", NUMERICSTRINGMATCH_OID, NULL};
  43. static const char *numericStringOrderingMatch_names[] = {"numericStringOrderingMatch", NUMERICSTRINGORDERINGMATCH_OID, NULL};
  44. static const char *numericStringSubstringsMatch_names[] = {"numericStringSubstringsMatch", NUMERICSTRINGSUBSTRINGSMATCH_OID, NULL};
  45. static char *numericStringSubstringsMatch_syntaxes[] = {NUMERICSTRING_SYNTAX_OID,NULL};
  46. static struct mr_plugin_def mr_plugin_table[] = {
  47. {
  48. {
  49. NUMERICSTRINGMATCH_OID,
  50. NULL /* no alias? */,
  51. "numericStringMatch",
  52. "The rule evaluates to TRUE if and only if the prepared "
  53. "attribute value character string and the prepared assertion value character "
  54. "string have the same number of characters and corresponding characters have "
  55. "the same code point.",
  56. NUMERICSTRING_SYNTAX_OID,
  57. 0 /* not obsolete */,
  58. NULL /* numstr syntax only for now */
  59. },
  60. {
  61. "numericStringMatch-mr",
  62. VENDOR,
  63. DS_PACKAGE_VERSION,
  64. "numericStringMatch matching rule plugin"
  65. }, /* plugin desc */
  66. numericStringMatch_names, /* matching rule name/oid/aliases */
  67. NULL,
  68. NULL,
  69. numstr_filter_ava,
  70. NULL,
  71. numstr_values2keys,
  72. numstr_assertion2keys,
  73. NULL,
  74. numstr_compare,
  75. NULL /* mr_normalise */
  76. },
  77. {
  78. {
  79. NUMERICSTRINGORDERINGMATCH_OID,
  80. NULL /* no alias? */,
  81. "numericStringOrderingMatch",
  82. "The rule evaluates to TRUE if and only if, "
  83. "in the code point collation order, the prepared attribute value character "
  84. "string appears earlier than the prepared assertion value character string; "
  85. "i.e., the attribute value is less than the assertion value.",
  86. NUMERICSTRING_SYNTAX_OID,
  87. 0 /* not obsolete */,
  88. NULL /* numstr syntax only for now */
  89. },
  90. {
  91. "numericStringOrderingMatch-mr",
  92. VENDOR,
  93. DS_PACKAGE_VERSION,
  94. "numericStringOrderingMatch matching rule plugin"
  95. }, /* plugin desc */
  96. numericStringOrderingMatch_names, /* matching rule name/oid/aliases */
  97. NULL,
  98. NULL,
  99. numstr_filter_ava,
  100. NULL,
  101. numstr_values2keys,
  102. numstr_assertion2keys,
  103. NULL,
  104. numstr_compare,
  105. NULL /* mr_normalise */
  106. },
  107. {
  108. {
  109. NUMERICSTRINGSUBSTRINGSMATCH_OID,
  110. NULL /* no alias? */,
  111. "numericStringSubstringsMatch",
  112. "The rule evaluates to TRUE if and only if (1) "
  113. "the prepared substrings of the assertion value match disjoint portions of "
  114. "the prepared attribute value, (2) an initial substring, if present, matches "
  115. "the beginning of the prepared attribute value character string, and (3) a "
  116. "final substring, if present, matches the end of the prepared attribute value "
  117. "character string.",
  118. "1.3.6.1.4.1.1466.115.121.1.58",
  119. 0 /* not obsolete */,
  120. numericStringSubstringsMatch_syntaxes
  121. }, /* matching rule desc */
  122. {
  123. "numericStringSubstringsMatch-mr",
  124. VENDOR,
  125. DS_PACKAGE_VERSION,
  126. "numericStringSubstringsMatch matching rule plugin"
  127. }, /* plugin desc */
  128. numericStringSubstringsMatch_names, /* matching rule name/oid/aliases */
  129. NULL,
  130. NULL,
  131. NULL,
  132. numstr_filter_sub,
  133. numstr_values2keys,
  134. NULL,
  135. numstr_assertion2keys_sub,
  136. numstr_compare,
  137. NULL /* mr_normalise */
  138. },
  139. };
  140. static size_t mr_plugin_table_size = sizeof(mr_plugin_table)/sizeof(mr_plugin_table[0]);
  141. static int
  142. matching_rule_plugin_init(Slapi_PBlock *pb)
  143. {
  144. return syntax_matching_rule_plugin_init(pb, mr_plugin_table, mr_plugin_table_size);
  145. }
  146. static int
  147. register_matching_rule_plugins(void)
  148. {
  149. return syntax_register_matching_rule_plugins(mr_plugin_table, mr_plugin_table_size, matching_rule_plugin_init);
  150. }
  151. int
  152. numstr_init( Slapi_PBlock *pb )
  153. {
  154. int rc, flags;
  155. LDAPDebug(LDAP_DEBUG_PLUGIN, "=> numstr_init\n", 0, 0, 0 );
  156. rc = slapi_pblock_set( pb, SLAPI_PLUGIN_VERSION,
  157. (void *) SLAPI_PLUGIN_VERSION_01 );
  158. rc |= slapi_pblock_set( pb, SLAPI_PLUGIN_DESCRIPTION,
  159. (void *)&pdesc );
  160. rc |= slapi_pblock_set( pb, SLAPI_PLUGIN_SYNTAX_FILTER_AVA,
  161. (void *) numstr_filter_ava );
  162. rc |= slapi_pblock_set( pb, SLAPI_PLUGIN_SYNTAX_VALUES2KEYS,
  163. (void *) numstr_values2keys );
  164. rc |= slapi_pblock_set( pb, SLAPI_PLUGIN_SYNTAX_ASSERTION2KEYS_AVA,
  165. (void *) numstr_assertion2keys );
  166. flags = SLAPI_PLUGIN_SYNTAX_FLAG_ORDERING;
  167. rc |= slapi_pblock_set( pb, SLAPI_PLUGIN_SYNTAX_FLAGS,
  168. (void *) &flags );
  169. rc |= slapi_pblock_set( pb, SLAPI_PLUGIN_SYNTAX_NAMES,
  170. (void *) names );
  171. rc |= slapi_pblock_set( pb, SLAPI_PLUGIN_SYNTAX_OID,
  172. (void *) NUMERICSTRING_SYNTAX_OID );
  173. rc |= slapi_pblock_set( pb, SLAPI_PLUGIN_SYNTAX_COMPARE,
  174. (void *) numstr_compare );
  175. rc |= slapi_pblock_set( pb, SLAPI_PLUGIN_SYNTAX_VALIDATE,
  176. (void *) numstr_validate );
  177. rc |= slapi_pblock_set( pb, SLAPI_PLUGIN_SYNTAX_NORMALIZE,
  178. (void *) numstr_normalize );
  179. rc |= register_matching_rule_plugins();
  180. LDAPDebug(LDAP_DEBUG_PLUGIN, "<= numstr_init %d\n", rc, 0, 0 );
  181. return( rc );
  182. }
  183. static int
  184. numstr_filter_ava( Slapi_PBlock *pb, struct berval *bvfilter,
  185. Slapi_Value **bvals, int ftype, Slapi_Value **retVal )
  186. {
  187. int filter_normalized = 0;
  188. int syntax = SYNTAX_SI | SYNTAX_CES;
  189. if (pb) {
  190. slapi_pblock_get( pb, SLAPI_PLUGIN_SYNTAX_FILTER_NORMALIZED,
  191. &filter_normalized );
  192. if (filter_normalized) {
  193. syntax |= SYNTAX_NORM_FILT;
  194. }
  195. }
  196. return( string_filter_ava( bvfilter, bvals, syntax,
  197. ftype, retVal ) );
  198. }
  199. static int
  200. numstr_filter_sub(
  201. Slapi_PBlock *pb,
  202. char *initial,
  203. char **any,
  204. char *final,
  205. Slapi_Value **bvals
  206. )
  207. {
  208. return( string_filter_sub( pb, initial, any, final, bvals, SYNTAX_SI | SYNTAX_CES ) );
  209. }
  210. static int
  211. numstr_values2keys( Slapi_PBlock *pb, Slapi_Value **vals, Slapi_Value ***ivals, int ftype )
  212. {
  213. return( string_values2keys( pb, vals, ivals, SYNTAX_SI | SYNTAX_CES,
  214. ftype ) );
  215. }
  216. static int
  217. numstr_assertion2keys( Slapi_PBlock *pb, Slapi_Value *val, Slapi_Value ***ivals, int ftype )
  218. {
  219. return(string_assertion2keys_ava( pb, val, ivals,
  220. SYNTAX_SI | SYNTAX_CES, ftype ));
  221. }
  222. static int
  223. numstr_assertion2keys_sub(
  224. Slapi_PBlock *pb,
  225. char *initial,
  226. char **any,
  227. char *final,
  228. Slapi_Value ***ivals
  229. )
  230. {
  231. return( string_assertion2keys_sub( pb, initial, any, final, ivals,
  232. SYNTAX_SI | SYNTAX_CES ) );
  233. }
  234. static int numstr_compare(
  235. struct berval *v1,
  236. struct berval *v2
  237. )
  238. {
  239. return value_cmp(v1, v2, SYNTAX_SI | SYNTAX_CES, 3 /* Normalise both values */);
  240. }
  241. /* return 0 if valid, non-0 if invalid */
  242. static int numstr_validate(
  243. struct berval *val
  244. )
  245. {
  246. int rc = 0; /* assume the value is valid */
  247. const char *p = NULL;
  248. /* Per RFC4517:
  249. *
  250. * NumericString = 1*(DIGIT / SPACE)
  251. */
  252. if (val != NULL) {
  253. for (p = val->bv_val; p < &(val->bv_val[val->bv_len]); p++) {
  254. if (!isdigit(*p) && !IS_SPACE(*p)) {
  255. rc = 1;
  256. goto exit;
  257. }
  258. }
  259. } else {
  260. rc = 1;
  261. }
  262. exit:
  263. return(rc);
  264. }
  265. static void numstr_normalize(
  266. Slapi_PBlock *pb,
  267. char *s,
  268. int trim_spaces,
  269. char **alt
  270. )
  271. {
  272. value_normalize_ext(s, SYNTAX_SI|SYNTAX_CES, trim_spaces, alt);
  273. return;
  274. }