]> git.sur5r.net Git - openldap/blob - servers/slapd/schemaparse.c
Apply dn_parent memory leak fix to bdb2
[openldap] / servers / slapd / schemaparse.c
1 /* schemaparse.c - routines to parse config file objectclass definitions */
2 /*
3  * Copyright 1998-1999 The OpenLDAP Foundation, All Rights Reserved.
4  * COPYING RESTRICTIONS APPLY, see COPYRIGHT file
5  */
6
7 #include "portable.h"
8
9 #include <stdio.h>
10
11 #include <ac/string.h>
12 #include <ac/socket.h>
13
14 #include "slap.h"
15 #include "ldap_schema.h"
16
17 static Avlnode          *object_classes = NULL;
18
19 int     global_schemacheck = 1; /* schemacheck on is default */
20
21 static void             oc_usage_old(void);
22 static void             oc_usage(void);
23
24 static char *err2text[] = {
25         "",
26         "Out of memory",
27         "Objectclass not found",
28         "Attribute type not found",
29         "Duplicate objectclass",
30         "Duplicate attributetype",
31         "Duplicate syntax",
32         "Duplicate matchingrule",
33         "OID or name required",
34         "Syntax or superior required",
35         "Matchingrule not found",
36         "Syntax not found",
37         "Syntax required"
38 };
39
40 char *
41 scherr2str(int code)
42 {
43         if ( code < 1 || code >= (sizeof(err2text)/sizeof(char *)) ) {
44                 return "Unknown error";
45         } else {
46                 return err2text[code];
47         }
48 }
49
50 void
51 parse_oc_old(
52     Backend     *be,
53     char        *fname,
54     int         lineno,
55     int         argc,
56     char        **argv
57 )
58 {
59         int             i;
60         char            last;
61         LDAP_OBJECT_CLASS       *oc;
62         int             code;
63         const char      *err;
64         char            **namep;
65
66         oc = (LDAP_OBJECT_CLASS *) ch_calloc( 1, sizeof(LDAP_OBJECT_CLASS) );
67         oc->oc_names = ch_calloc( 2, sizeof(char *) );
68         oc->oc_names[0] = ch_strdup( argv[1] );
69         oc->oc_names[1] = NULL;
70         if ( strcasecmp( oc->oc_names[0], "top" ) ) {
71                 oc->oc_kind = LDAP_SCHEMA_STRUCTURAL;
72         }
73         for ( i = 2; i < argc; i++ ) {
74                 /* required attributes */
75                 if ( strcasecmp( argv[i], "requires" ) == 0 ) {
76                         do {
77                                 i++;
78                                 if ( i < argc ) {
79                                         char **s = str2charray( argv[i], "," );
80                                         last = argv[i][strlen( argv[i] ) - 1];
81                                         charray_merge( &oc->oc_at_oids_must, s );
82                                         charray_free( s );
83                                 }
84                         } while ( i < argc && last == ',' );
85
86                 /* optional attributes */
87                 } else if ( strcasecmp( argv[i], "allows" ) == 0 ) {
88                         do {
89                                 i++;
90                                 if ( i < argc ) {
91                                         char **s = str2charray( argv[i], "," );
92                                         last = argv[i][strlen( argv[i] ) - 1];
93                                         
94                                         charray_merge( &oc->oc_at_oids_may, s );
95                                         charray_free( s );
96                                 }
97                         } while ( i < argc && last == ',' );
98
99                 } else {
100                         fprintf( stderr,
101             "%s: line %d: expecting \"requires\" or \"allows\" got \"%s\"\n",
102                             fname, lineno, argv[i] );
103                         oc_usage_old();
104                 }
105         }
106
107         /*
108          * There was no requirement in the old schema that all attributes
109          * types were defined before use and they would just default to
110          * SYNTAX_CIS.  To support this, we need to make attribute types
111          * out of thin air.
112          */
113         if ( oc->oc_at_oids_must ) {
114                 namep = oc->oc_at_oids_must;
115                 while ( *namep ) {
116                         code = at_fake_if_needed( *namep );
117                         if ( code ) {
118                                 fprintf( stderr, "%s: line %d: %s %s\n",
119                                          fname, lineno, scherr2str(code), *namep);
120                                 exit( EXIT_FAILURE );
121                         }
122                         namep++;
123                 }
124         }
125         if ( oc->oc_at_oids_may ) {
126                 namep = oc->oc_at_oids_may;
127                 while ( *namep ) {
128                         code = at_fake_if_needed( *namep );
129                         if ( code ) {
130                                 fprintf( stderr, "%s: line %d: %s %s\n",
131                                          fname, lineno, scherr2str(code), *namep);
132                                 exit( EXIT_FAILURE );
133                         }
134                         namep++;
135                 }
136         }
137         
138         code = oc_add(oc,&err);
139         if ( code ) {
140                 fprintf( stderr, "%s: line %d: %s %s\n",
141                          fname, lineno, scherr2str(code), err);
142                 exit( EXIT_FAILURE );
143         }
144         ldap_memfree(oc);
145 }
146
147 void
148 parse_oc(
149     char        *fname,
150     int         lineno,
151     char        *line
152 )
153 {
154         LDAP_OBJECT_CLASS *oc;
155         int             code;
156         const char      *err;
157
158         oc = ldap_str2objectclass(line,&code,&err);
159         if ( !oc ) {
160                 fprintf( stderr, "%s: line %d: %s before %s\n",
161                          fname, lineno, ldap_scherr2str(code), err );
162                 oc_usage();
163         }
164         code = oc_add(oc,&err);
165         if ( code ) {
166                 fprintf( stderr, "%s: line %d: %s %s\n",
167                          fname, lineno, scherr2str(code), err);
168                 exit( EXIT_FAILURE );
169         }
170         ldap_memfree(oc);
171 }
172
173 static void
174 oc_usage( void )
175 {
176         fprintf( stderr, "ObjectClassDescription = \"(\" whsp\n");
177         fprintf( stderr, "  numericoid whsp      ; ObjectClass identifier\n");
178         fprintf( stderr, "  [ \"NAME\" qdescrs ]\n");
179         fprintf( stderr, "  [ \"DESC\" qdstring ]\n");
180         fprintf( stderr, "  [ \"OBSOLETE\" whsp ]\n");
181         fprintf( stderr, "  [ \"SUP\" oids ]       ; Superior ObjectClasses\n");
182         fprintf( stderr, "  [ ( \"ABSTRACT\" / \"STRUCTURAL\" / \"AUXILIARY\" ) whsp ]\n");
183         fprintf( stderr, "                       ; default structural\n");
184         fprintf( stderr, "  [ \"MUST\" oids ]      ; AttributeTypes\n");
185         fprintf( stderr, "  [ \"MAY\" oids ]       ; AttributeTypes\n");
186         fprintf( stderr, "whsp \")\"\n");
187         exit( EXIT_FAILURE );
188 }
189
190 static void
191 oc_usage_old( void )
192 {
193         fprintf( stderr, "<oc clause> ::= objectclass <ocname>\n" );
194         fprintf( stderr, "                [ requires <attrlist> ]\n" );
195         fprintf( stderr, "                [ allows <attrlist> ]\n" );
196         exit( EXIT_FAILURE );
197 }
198
199 static void
200 at_usage( void )
201 {
202         fprintf( stderr, "AttributeTypeDescription = \"(\" whsp\n");
203         fprintf( stderr, "  numericoid whsp      ; AttributeType identifier\n");
204         fprintf( stderr, "  [ \"NAME\" qdescrs ]             ; name used in AttributeType\n");
205         fprintf( stderr, "  [ \"DESC\" qdstring ]            ; description\n");
206         fprintf( stderr, "  [ \"OBSOLETE\" whsp ]\n");
207         fprintf( stderr, "  [ \"SUP\" woid ]                 ; derived from this other\n");
208         fprintf( stderr, "                                 ; AttributeType\n");
209         fprintf( stderr, "  [ \"EQUALITY\" woid ]            ; Matching Rule name\n");
210         fprintf( stderr, "  [ \"ORDERING\" woid ]            ; Matching Rule name\n");
211         fprintf( stderr, "  [ \"SUBSTR\" woid ]              ; Matching Rule name\n");
212         fprintf( stderr, "  [ \"SYNTAX\" whsp noidlen whsp ] ; see section 4.3\n");
213         fprintf( stderr, "  [ \"SINGLE-VALUE\" whsp ]        ; default multi-valued\n");
214         fprintf( stderr, "  [ \"COLLECTIVE\" whsp ]          ; default not collective\n");
215         fprintf( stderr, "  [ \"NO-USER-MODIFICATION\" whsp ]; default user modifiable\n");
216         fprintf( stderr, "  [ \"USAGE\" whsp AttributeUsage ]; default userApplications\n");
217         fprintf( stderr, "                                 ; userApplications\n");
218         fprintf( stderr, "                                 ; directoryOperation\n");
219         fprintf( stderr, "                                 ; distributedOperation\n");
220         fprintf( stderr, "                                 ; dSAOperation\n");
221         fprintf( stderr, "whsp \")\"\n");
222         exit( EXIT_FAILURE );
223 }
224
225 void
226 parse_at(
227     char        *fname,
228     int         lineno,
229     char        *line
230 )
231 {
232         LDAP_ATTRIBUTE_TYPE *at;
233         int             code;
234         const char      *err;
235
236         at = ldap_str2attributetype(line,&code,&err);
237         if ( !at ) {
238                 fprintf( stderr, "%s: line %d: %s before %s\n",
239                          fname, lineno, ldap_scherr2str(code), err );
240                 at_usage();
241         }
242         code = at_add(at,&err);
243         if ( code ) {
244                 fprintf( stderr, "%s: line %d: %s %s\n",
245                          fname, lineno, scherr2str(code), err);
246                 exit( EXIT_FAILURE );
247         }
248         ldap_memfree(at);
249 }