2005-01-31 Zoltan Varga <vargaz@freemail.hu>
[mono.git] / mcs / class / Novell.Directory.Ldap / Novell.Directory.Ldap.Utilclass / SchemaParser.cs
1 /******************************************************************************
2 * The MIT License
3 * Copyright (c) 2003 Novell Inc.  www.novell.com
4
5 * Permission is hereby granted, free of charge, to any person obtaining  a copy
6 * of this software and associated documentation files (the Software), to deal
7 * in the Software without restriction, including  without limitation the rights
8 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 
9 * copies of the Software, and to  permit persons to whom the Software is 
10 * furnished to do so, subject to the following conditions:
11
12 * The above copyright notice and this permission notice shall be included in 
13 * all copies or substantial portions of the Software.
14
15 * THE SOFTWARE IS PROVIDED AS IS, WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 
16 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 
17 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 
19 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 * SOFTWARE.
22 *******************************************************************************/
23 //
24 // Novell.Directory.Ldap.LdapAttributeSchema.cs
25 //
26 // Author:
27 //   Sunil Kumar (Sunilk@novell.com)
28 //
29 // (C) 2003 Novell, Inc (http://www.novell.com)
30 //
31
32 using System;
33 using LdapObjectClassSchema = Novell.Directory.Ldap.LdapObjectClassSchema;
34 using LdapAttributeSchema = Novell.Directory.Ldap.LdapAttributeSchema;
35
36 namespace Novell.Directory.Ldap.Utilclass
37 {
38         
39         public class SchemaParser
40         {
41                 private void  InitBlock()
42                 {
43                         usage = LdapAttributeSchema.USER_APPLICATIONS;
44                         qualifiers = new System.Collections.ArrayList();
45                 }
46                 virtual public System.String RawString
47                 {
48                         get
49                         {
50                                 return rawString;
51                         }
52                         
53                         set
54                         {
55                                 this.rawString = value;
56                         }
57                         
58                 }
59                 virtual public System.String[] Names
60                 {
61                         get
62                         {
63                                 return names;
64                         }
65                         
66                 }
67                 virtual public System.Collections.IEnumerator Qualifiers
68                 {
69                         get
70                         {
71                                 return new ArrayEnumeration(qualifiers.ToArray());
72                         }
73                         
74                 }
75                 virtual public System.String ID
76                 {
77                         get
78                         {
79                                 return id;
80                         }
81                         
82                 }
83                 virtual public System.String Description
84                 {
85                         get
86                         {
87                                 return description;
88                         }
89                         
90                 }
91                 virtual public System.String Syntax
92                 {
93                         get
94                         {
95                                 return syntax;
96                         }
97                         
98                 }
99                 virtual public System.String Superior
100                 {
101                         get
102                         {
103                                 return superior;
104                         }
105                         
106                 }
107                 virtual public bool Single
108                 {
109                         get
110                         {
111                                 return single;
112                         }
113                         
114                 }
115                 virtual public bool Obsolete
116                 {
117                         get
118                         {
119                                 return obsolete;
120                         }
121                         
122                 }
123                 virtual public System.String Equality
124                 {
125                         get
126                         {
127                                 return equality;
128                         }
129                         
130                 }
131                 virtual public System.String Ordering
132                 {
133                         get
134                         {
135                                 return ordering;
136                         }
137                         
138                 }
139                 virtual public System.String Substring
140                 {
141                         get
142                         {
143                                 return substring;
144                         }
145                         
146                 }
147                 virtual public bool Collective
148                 {
149                         get
150                         {
151                                 return collective;
152                         }
153                         
154                 }
155                 virtual public bool UserMod
156                 {
157                         get
158                         {
159                                 return userMod;
160                         }
161                         
162                 }
163                 virtual public int Usage
164                 {
165                         get
166                         {
167                                 return usage;
168                         }
169                         
170                 }
171                 virtual public int Type
172                 {
173                         get
174                         {
175                                 return type;
176                         }
177                         
178                 }
179                 virtual public System.String[] Superiors
180                 {
181                         get
182                         {
183                                 return superiors;
184                         }
185                         
186                 }
187                 virtual public System.String[] Required
188                 {
189                         get
190                         {
191                                 return required;
192                         }
193                         
194                 }
195                 virtual public System.String[] Optional
196                 {
197                         get
198                         {
199                                 return optional;
200                         }
201                         
202                 }
203                 virtual public System.String[] Auxiliary
204                 {
205                         get
206                         {
207                                 return auxiliary;
208                         }
209                         
210                 }
211                 virtual public System.String[] Precluded
212                 {
213                         get
214                         {
215                                 return precluded;
216                         }
217                         
218                 }
219                 virtual public System.String[] Applies
220                 {
221                         get
222                         {
223                                 return applies;
224                         }
225                         
226                 }
227                 virtual public System.String NameForm
228                 {
229                         get
230                         {
231                                 return nameForm;
232                         }
233                         
234                 }
235                 virtual public System.String ObjectClass
236                 {
237                         get
238                         {
239                                 return nameForm;
240                         }
241                         
242                 }
243                 
244                 internal System.String rawString;
245                 internal System.String[] names = null;
246                 internal System.String id;
247                 internal System.String description;
248                 internal System.String syntax;
249                 internal System.String superior;
250                 internal System.String nameForm;
251                 internal System.String objectClass;
252                 internal System.String[] superiors;
253                 internal System.String[] required;
254                 internal System.String[] optional;
255                 internal System.String[] auxiliary;
256                 internal System.String[] precluded;
257                 internal System.String[] applies;
258                 internal bool single = false;
259                 internal bool obsolete = false;
260                 internal System.String equality;
261                 internal System.String ordering;
262                 internal System.String substring;
263                 internal bool collective = false;
264                 internal bool userMod = true;
265                 internal int usage;
266                 internal int type = - 1;
267                 internal int result;
268                 internal System.Collections.ArrayList qualifiers;
269                 
270                 public SchemaParser(System.String aString)
271                 {
272                         InitBlock();
273                         
274                         int index;
275                         
276                         if ((index = aString.IndexOf((System.Char) '\\')) != - 1)
277                         {
278                                 /*
279                                 * Unless we escape the slash, StreamTokenizer will interpret the
280                                 * single slash and convert it assuming octal values.
281                                 * Two successive back slashes are intrepreted as one backslash.
282                                 */
283                                 System.Text.StringBuilder newString = new System.Text.StringBuilder(aString.Substring(0, (index) - (0)));
284                                 for (int i = index; i < aString.Length; i++)
285                                 {
286                                         newString.Append(aString[i]);
287                                         if (aString[i] == '\\')
288                                         {
289                                                 newString.Append('\\');
290                                         }
291                                 }
292                                 rawString = newString.ToString();
293                         }
294                         else
295                         {
296                                 rawString = aString;
297                         }
298                         
299                         SchemaTokenCreator st2 = new SchemaTokenCreator(new System.IO.StringReader(rawString));
300                         st2.OrdinaryCharacter('.');
301                         st2.OrdinaryCharacters('0', '9');
302                         st2.OrdinaryCharacter('{');
303                         st2.OrdinaryCharacter('}');
304                         st2.OrdinaryCharacter('_');
305                         st2.OrdinaryCharacter(';');
306                         st2.WordCharacters('.', '9');
307                         st2.WordCharacters('{', '}');
308                         st2.WordCharacters('_', '_');
309                         st2.WordCharacters(';', ';');
310                         //First parse out the OID
311                         try
312                         {
313                                 System.String currName;
314                                 if ((int)TokenTypes.EOF != st2.nextToken())
315                                 {
316                                         if (st2.lastttype == '(')
317                                         {
318                                                 if ((int)TokenTypes.WORD == st2.nextToken())
319                                                 {
320                                                         id = st2.StringValue;
321                                                 }
322                                                 while ((int)TokenTypes.EOF != st2.nextToken())
323                                                 {
324                                                         if (st2.lastttype == (int)TokenTypes.WORD)
325                                                         {
326                                                                 if (st2.StringValue.ToUpper().Equals("NAME".ToUpper()))
327                                                                 {
328                                                                         if (st2.nextToken() == '\'')
329                                                                         {
330                                                                                 names = new System.String[1];
331                                                                                 names[0] = st2.StringValue;
332                                                                         }
333                                                                         else
334                                                                         {
335                                                                                 if (st2.lastttype == '(')
336                                                                                 {
337                                                                                         System.Collections.ArrayList nameList = new System.Collections.ArrayList();
338                                                                                         while (st2.nextToken() == '\'')
339                                                                                         {
340                                                                                                 if ((System.Object) st2.StringValue != null)
341                                                                                                 {
342                                                                                                         nameList.Add(st2.StringValue);
343                                                                                                 }
344                                                                                         }
345                                                                                         if (nameList.Count > 0)
346                                                                                         {
347                                                                                                 names = new System.String[nameList.Count];
348                                                                                                 SupportClass.ArrayListSupport.ToArray(nameList, names);
349                                                                                         }
350                                                                                 }
351                                                                         }
352                                                                         continue;
353                                                                 }
354                                                                 if (st2.StringValue.ToUpper().Equals("DESC".ToUpper()))
355                                                                 {
356                                                                         if (st2.nextToken() == '\'')
357                                                                         {
358                                                                                 description = st2.StringValue;
359                                                                         }
360                                                                         continue;
361                                                                 }
362                                                                 if (st2.StringValue.ToUpper().Equals("SYNTAX".ToUpper()))
363                                                                 {
364                                                                         result = st2.nextToken();
365                                                                         if ((result == (int)TokenTypes.WORD) || (result == '\''))
366                                                                         //Test for non-standard schema
367                                                                         {
368                                                                                 syntax = st2.StringValue;
369                                                                         }
370                                                                         continue;
371                                                                 }
372                                                                 if (st2.StringValue.ToUpper().Equals("EQUALITY".ToUpper()))
373                                                                 {
374                                                                         if (st2.nextToken() == (int)TokenTypes.WORD)
375                                                                         {
376                                                                                 equality = st2.StringValue;
377                                                                         }
378                                                                         continue;
379                                                                 }
380                                                                 if (st2.StringValue.ToUpper().Equals("ORDERING".ToUpper()))
381                                                                 {
382                                                                         if (st2.nextToken() == (int)TokenTypes.WORD)
383                                                                         {
384                                                                                 ordering = st2.StringValue;
385                                                                         }
386                                                                         continue;
387                                                                 }
388                                                                 if (st2.StringValue.ToUpper().Equals("SUBSTR".ToUpper()))
389                                                                 {
390                                                                         if (st2.nextToken() == (int)TokenTypes.WORD)
391                                                                         {
392                                                                                 substring = st2.StringValue;
393                                                                         }
394                                                                         continue;
395                                                                 }
396                                                                 if (st2.StringValue.ToUpper().Equals("FORM".ToUpper()))
397                                                                 {
398                                                                         if (st2.nextToken() == (int)TokenTypes.WORD)
399                                                                         {
400                                                                                 nameForm = st2.StringValue;
401                                                                         }
402                                                                         continue;
403                                                                 }
404                                                                 if (st2.StringValue.ToUpper().Equals("OC".ToUpper()))
405                                                                 {
406                                                                         if (st2.nextToken() == (int)TokenTypes.WORD)
407                                                                         {
408                                                                                 objectClass = st2.StringValue;
409                                                                         }
410                                                                         continue;
411                                                                 }
412                                                                 if (st2.StringValue.ToUpper().Equals("SUP".ToUpper()))
413                                                                 {
414                                                                         System.Collections.ArrayList values = new System.Collections.ArrayList();
415                                                                         st2.nextToken();
416                                                                         if (st2.lastttype == '(')
417                                                                         {
418                                                                                 st2.nextToken();
419                                                                                 while (st2.lastttype != ')')
420                                                                                 {
421                                                                                         if (st2.lastttype != '$')
422                                                                                         {
423                                                                                                 values.Add(st2.StringValue);
424                                                                                         }
425                                                                                         st2.nextToken();
426                                                                                 }
427                                                                         }
428                                                                         else
429                                                                         {
430                                                                                 values.Add(st2.StringValue);
431                                                                                 superior = st2.StringValue;
432                                                                         }
433                                                                         if (values.Count > 0)
434                                                                         {
435                                                                                 superiors = new System.String[values.Count];
436                                                                                 SupportClass.ArrayListSupport.ToArray(values, superiors);
437                                                                         }
438                                                                         continue;
439                                                                 }
440                                                                 if (st2.StringValue.ToUpper().Equals("SINGLE-VALUE".ToUpper()))
441                                                                 {
442                                                                         single = true;
443                                                                         continue;
444                                                                 }
445                                                                 if (st2.StringValue.ToUpper().Equals("OBSOLETE".ToUpper()))
446                                                                 {
447                                                                         obsolete = true;
448                                                                         continue;
449                                                                 }
450                                                                 if (st2.StringValue.ToUpper().Equals("COLLECTIVE".ToUpper()))
451                                                                 {
452                                                                         collective = true;
453                                                                         continue;
454                                                                 }
455                                                                 if (st2.StringValue.ToUpper().Equals("NO-USER-MODIFICATION".ToUpper()))
456                                                                 {
457                                                                         userMod = false;
458                                                                         continue;
459                                                                 }
460                                                                 if (st2.StringValue.ToUpper().Equals("MUST".ToUpper()))
461                                                                 {
462                                                                         System.Collections.ArrayList values = new System.Collections.ArrayList();
463                                                                         st2.nextToken();
464                                                                         if (st2.lastttype == '(')
465                                                                         {
466                                                                                 st2.nextToken();
467                                                                                 while (st2.lastttype != ')')
468                                                                                 {
469                                                                                         if (st2.lastttype != '$')
470                                                                                         {
471                                                                                                 values.Add(st2.StringValue);
472                                                                                         }
473                                                                                         st2.nextToken();
474                                                                                 }
475                                                                         }
476                                                                         else
477                                                                         {
478                                                                                 values.Add(st2.StringValue);
479                                                                         }
480                                                                         if (values.Count > 0)
481                                                                         {
482                                                                                 required = new System.String[values.Count];
483                                                                                 SupportClass.ArrayListSupport.ToArray(values, required);
484                                                                         }
485                                                                         continue;
486                                                                 }
487                                                                 if (st2.StringValue.ToUpper().Equals("MAY".ToUpper()))
488                                                                 {
489                                                                         System.Collections.ArrayList values = new System.Collections.ArrayList();
490                                                                         st2.nextToken();
491                                                                         if (st2.lastttype == '(')
492                                                                         {
493                                                                                 st2.nextToken();
494                                                                                 while (st2.lastttype != ')')
495                                                                                 {
496                                                                                         if (st2.lastttype != '$')
497                                                                                         {
498                                                                                                 values.Add(st2.StringValue);
499                                                                                         }
500                                                                                         st2.nextToken();
501                                                                                 }
502                                                                         }
503                                                                         else
504                                                                         {
505                                                                                 values.Add(st2.StringValue);
506                                                                         }
507                                                                         if (values.Count > 0)
508                                                                         {
509                                                                                 optional = new System.String[values.Count];
510                                                                                 SupportClass.ArrayListSupport.ToArray(values, optional);
511                                                                         }
512                                                                         continue;
513                                                                 }
514
515                                                                 if (st2.StringValue.ToUpper().Equals("NOT".ToUpper()))
516                                                                 {
517                                                                         System.Collections.ArrayList values = new System.Collections.ArrayList();
518                                                                         st2.nextToken();
519                                                                         if (st2.lastttype == '(')
520                                                                         {
521                                                                                 st2.nextToken();
522                                                                                 while (st2.lastttype != ')')
523                                                                                 {
524                                                                                         if (st2.lastttype != '$')
525                                                                                         {
526                                                                                                 values.Add(st2.StringValue);
527                                                                                         }
528                                                                                         st2.nextToken();
529                                                                                 }
530                                                                         }
531                                                                         else
532                                                                         {
533                                                                                 values.Add(st2.StringValue);
534                                                                         }
535                                                                         if (values.Count > 0)
536                                                                         {
537                                                                                 precluded = new System.String[values.Count];
538                                                                                 SupportClass.ArrayListSupport.ToArray(values, precluded);
539                                                                         }
540                                                                         continue;
541                                                                 }
542                                                                 if (st2.StringValue.ToUpper().Equals("AUX".ToUpper()))
543                                                                 {
544                                                                         System.Collections.ArrayList values = new System.Collections.ArrayList();
545                                                                         st2.nextToken();
546                                                                         if (st2.lastttype == '(')
547                                                                         {
548                                                                                 st2.nextToken();
549                                                                                 while (st2.lastttype != ')')
550                                                                                 {
551                                                                                         if (st2.lastttype != '$')
552                                                                                         {
553                                                                                                 values.Add(st2.StringValue);
554                                                                                         }
555                                                                                         st2.nextToken();
556                                                                                 }
557                                                                         }
558                                                                         else
559                                                                         {
560                                                                                 values.Add(st2.StringValue);
561                                                                         }
562                                                                         if (values.Count > 0)
563                                                                         {
564                                                                                 auxiliary = new System.String[values.Count];
565                                                                                 SupportClass.ArrayListSupport.ToArray(values, auxiliary);
566                                                                         }
567                                                                         continue;
568                                                                 }
569                                                                 if (st2.StringValue.ToUpper().Equals("ABSTRACT".ToUpper()))
570                                                                 {
571                                                                         type = LdapObjectClassSchema.ABSTRACT;
572                                                                         continue;
573                                                                 }
574                                                                 if (st2.StringValue.ToUpper().Equals("STRUCTURAL".ToUpper()))
575                                                                 {
576                                                                         type = LdapObjectClassSchema.STRUCTURAL;
577                                                                         continue;
578                                                                 }
579                                                                 if (st2.StringValue.ToUpper().Equals("AUXILIARY".ToUpper()))
580                                                                 {
581                                                                         type = LdapObjectClassSchema.AUXILIARY;
582                                                                         continue;
583                                                                 }
584                                                                 if (st2.StringValue.ToUpper().Equals("USAGE".ToUpper()))
585                                                                 {
586                                                                         if (st2.nextToken() == (int)TokenTypes.WORD)
587                                                                         {
588                                                                                 currName = st2.StringValue;
589                                                                                 if (currName.ToUpper().Equals("directoryOperation".ToUpper()))
590                                                                                 {
591                                                                                         usage = LdapAttributeSchema.DIRECTORY_OPERATION;
592                                                                                 }
593                                                                                 else if (currName.ToUpper().Equals("distributedOperation".ToUpper()))
594                                                                                 {
595                                                                                         usage = LdapAttributeSchema.DISTRIBUTED_OPERATION;
596                                                                                 }
597                                                                                 else if (currName.ToUpper().Equals("dSAOperation".ToUpper()))
598                                                                                 {
599                                                                                         usage = LdapAttributeSchema.DSA_OPERATION;
600                                                                                 }
601                                                                                 else if (currName.ToUpper().Equals("userApplications".ToUpper()))
602                                                                                 {
603                                                                                         usage = LdapAttributeSchema.USER_APPLICATIONS;
604                                                                                 }
605                                                                         }
606                                                                         continue;
607                                                                 }
608                                                                 if (st2.StringValue.ToUpper().Equals("APPLIES".ToUpper()))
609                                                                 {
610                                                                         System.Collections.ArrayList values = new System.Collections.ArrayList();
611                                                                         st2.nextToken();
612                                                                         if (st2.lastttype == '(')
613                                                                         {
614                                                                                 st2.nextToken();
615                                                                                 while (st2.lastttype != ')')
616                                                                                 {
617                                                                                         if (st2.lastttype != '$')
618                                                                                         {
619                                                                                                 values.Add(st2.StringValue);
620                                                                                         }
621                                                                                         st2.nextToken();
622                                                                                 }
623                                                                         }
624                                                                         else
625                                                                         {
626                                                                                 values.Add(st2.StringValue);
627                                                                         }
628                                                                         if (values.Count > 0)
629                                                                         {
630                                                                                 applies = new System.String[values.Count];
631                                                                                 SupportClass.ArrayListSupport.ToArray(values, applies);
632                                                                         }
633                                                                         continue;
634                                                                 }
635                                                                 currName = st2.StringValue;
636                                                                 AttributeQualifier q = parseQualifier(st2, currName);
637                                                                 if (q != null)
638                                                                 {
639                                                                         qualifiers.Add(q);
640                                                                 }
641                                                                 continue;
642                                                         }
643                                                 }
644                                         }
645                                 }
646                         }
647                         catch (System.IO.IOException e)
648                         {
649                                 throw e;
650                         }
651                 }
652                 
653                 private AttributeQualifier parseQualifier(SchemaTokenCreator st, System.String name)
654                 {
655                         System.Collections.ArrayList values = new System.Collections.ArrayList(5);
656                         try
657                         {
658                                 if (st.nextToken() == '\'')
659                                 {
660                                         values.Add(st.StringValue);
661                                 }
662                                 else
663                                 {
664                                         if (st.lastttype == '(')
665                                         {
666                                                 while (st.nextToken() == '\'')
667                                                 {
668                                                         values.Add(st.StringValue);
669                                                 }
670                                         }
671                                 }
672                         }
673                         catch (System.IO.IOException e)
674                         {
675                                 throw e;
676                         }
677                         System.String[] valArray = new System.String[values.Count];
678                         valArray = (System.String[]) SupportClass.ArrayListSupport.ToArray(values, valArray);
679                         return new AttributeQualifier(name, valArray);
680                 }
681         }
682 }