Diff for /servers/slapd/schemaparse.c between versions 1.12 and 1.12.8.14

version 1.12, 1999/06/15 10:28:54 version 1.12.8.14, 2002/01/04 20:38:31
Line 1 Line 1
 /* schemaparse.c - routines to parse config file objectclass definitions */  /* schemaparse.c - routines to parse config file objectclass definitions */
   /* $OpenLDAP: pkg/ldap/servers/slapd/schemaparse.c,v 1.12.8.13 2001/10/11 16:49:04 kurt Exp $ */
   /*
    * Copyright 1998-2002 The OpenLDAP Foundation, All Rights Reserved.
    * COPYING RESTRICTIONS APPLY, see COPYRIGHT file
    */
   
 #include "portable.h"  #include "portable.h"
   
 #include <stdio.h>  #include <stdio.h>
   
   #include <ac/ctype.h>
 #include <ac/string.h>  #include <ac/string.h>
 #include <ac/socket.h>  #include <ac/socket.h>
   
 #include "slap.h"  #include "slap.h"
 #include "ldap_schema.h"  #include "ldap_schema.h"
   
 static Avlnode          *object_classes = NULL;  
   
 int     global_schemacheck = 1; /* schemacheck on is default */  int     global_schemacheck = 1; /* schemacheck on is default */
   
 static void             oc_usage_old(void);  static void             oc_usage(void); 
 static void             oc_usage(void);  static void             at_usage(void);
   
 static char *err2text[] = {  static char *const err2text[] = {
         "",          "Success",
         "Out of memory",          "Out of memory",
         "Objectclass not found",          "ObjectClass not found",
         "Attribute type not found",          "ObjectClass inappropriate SUPerior",
         "Duplicate objectclass",          "AttributeType not found",
         "Duplicate attributetype",          "AttributeType inappropriate USAGE",
         "Duplicate syntax",          "Duplicate objectClass",
         "Duplicate matchingrule",          "Duplicate attributeType",
           "Duplicate ldapSyntax",
           "Duplicate matchingRule",
         "OID or name required",          "OID or name required",
         "Syntax or superior required",          "SYNTAX or SUPerior required",
         "Matchingrule not found",          "MatchingRule not found",
         "Syntax not found",          "Syntax not found",
         "Syntax required"          "Syntax required",
           "Qualifier not supported",
           "Invalid NAME"
 };  };
   
 char *  char *
 scherr2str(int code)  scherr2str(int code)
 {  {
         if ( code < 1 || code >= (sizeof(err2text)/sizeof(char *)) ) {          if ( code < 0 || code >= (sizeof(err2text)/sizeof(char *)) ) {
                 return "Unknown error";                  return "Unknown error";
         } else {          } else {
                 return err2text[code];                  return err2text[code];
         }          }
 }  }
   
 void  /* check schema descr validity */
 parse_oc_old(  int slap_valid_descr( const char *descr )
     Backend     *be,  
     char        *fname,  
     int         lineno,  
     int         argc,  
     char        **argv  
 )  
 {  {
         int             i;          int i=0;
         char            last;  
         LDAP_OBJECT_CLASS       *oc;  
         int             code;  
         const char      *err;  
         char            **namep;  
   
         oc = (LDAP_OBJECT_CLASS *) ch_calloc( 1, sizeof(LDAP_OBJECT_CLASS) );          if( !DESC_LEADCHAR( descr[i] ) ) {
         oc->oc_names = ch_calloc( 2, sizeof(char *) );                  return 0;
         oc->oc_names[0] = ch_strdup( argv[1] );          }
         oc->oc_names[1] = NULL;  
         if ( strcasecmp( oc->oc_names[0], "top" ) ) {  
                 oc->oc_kind = LDAP_SCHEMA_STRUCTURAL;  
         }  
         for ( i = 2; i < argc; i++ ) {  
                 /* required attributes */  
                 if ( strcasecmp( argv[i], "requires" ) == 0 ) {  
                         do {  
                                 i++;  
                                 if ( i < argc ) {  
                                         char **s = str2charray( argv[i], "," );  
                                         last = argv[i][strlen( argv[i] ) - 1];  
                                         charray_merge( &oc->oc_at_oids_must, s );  
                                         charray_free( s );  
                                 }  
                         } while ( i < argc && last == ',' );  
   
                 /* optional attributes */  
                 } else if ( strcasecmp( argv[i], "allows" ) == 0 ) {  
                         do {  
                                 i++;  
                                 if ( i < argc ) {  
                                         char **s = str2charray( argv[i], "," );  
                                         last = argv[i][strlen( argv[i] ) - 1];  
                                           
                                         charray_merge( &oc->oc_at_oids_may, s );  
                                         charray_free( s );  
                                 }  
                         } while ( i < argc && last == ',' );  
   
                 } else {          while( descr[++i] ) {
                         fprintf( stderr,                  if( !DESC_CHAR( descr[i] ) ) {
             "%s: line %d: expecting \"requires\" or \"allows\" got \"%s\"\n",                          return 0;
                             fname, lineno, argv[i] );  
                         oc_usage_old();  
                 }                  }
         }          }
   
         /*          return 1;
          * There was no requirement in the old schema that all attributes  }
          * types were defined before use and they would just default to  
          * SYNTAX_CIS.  To support this, we need to make attribute types  
          * out of thin air.  /* OID Macros */
          */  
         if ( oc->oc_at_oids_must ) {  /* String compare with delimiter check. Return 0 if not
                 namep = oc->oc_at_oids_must;   * matched, otherwise return length matched.
                 while ( *namep ) {   */
                         code = at_fake_if_needed( *namep );  int
                         if ( code ) {  dscompare(const char *s1, const char *s2, char delim)
                                 fprintf( stderr, "%s: line %d: %s %s\n",  {
                                          fname, lineno, scherr2str(code), *namep);          const char *orig = s1;
                                 exit( 1 );          while (*s1++ == *s2++)
                         }                  if (!s1[-1]) break;
                         namep++;          --s1;
                 }          --s2;
           if (!*s1 && (!*s2 || *s2 == delim))
                   return s1 - orig;
           return 0;
   }
   
   static OidMacro *om_list = NULL;
   
   /* Replace an OID Macro invocation with its full numeric OID.
    * If the macro is used with "macroname:suffix" append ".suffix"
    * to the expansion.
    */
   static char *
   find_oidm(char *oid)
   {
           OidMacro *om;
   
           /* OID macros must start alpha */
           if ( OID_LEADCHAR( *oid ) )     {
                   return oid;
         }          }
         if ( oc->oc_at_oids_may ) {  
                 namep = oc->oc_at_oids_may;      for (om = om_list; om; om=om->som_next) {
                 while ( *namep ) {                  char **names = om->som_names;
                         code = at_fake_if_needed( *namep );  
                         if ( code ) {                  if( names == NULL ) {
                                 fprintf( stderr, "%s: line %d: %s %s\n",                          continue;
                                          fname, lineno, scherr2str(code), *namep);                  }
                                 exit( 1 );  
                   for( ; *names != NULL ; names++ ) {
                           int pos = dscompare(*names, oid, ':');
   
                           if( pos ) {
                                   int suflen = strlen(oid + pos);
                                   char *new = ch_calloc(1,
                                           om->som_oid.bv_len + suflen + 1);
                                   strcpy(new, om->som_oid.bv_val);
   
                                   if( suflen ) {
                                           suflen = om->som_oid.bv_len;
                                           new[suflen++] = '.';
                                           strcpy(new+suflen, oid+pos+1);
                                   }
                                   return new;
                         }                          }
                         namep++;  
                 }                  }
         }          }
                   return NULL;
         code = oc_add(oc,&err);  }
         if ( code ) {  
                 fprintf( stderr, "%s: line %d: %s %s\n",  int
                          fname, lineno, scherr2str(code), err);  parse_oidm(
                 exit( 1 );      const char  *fname,
       int         lineno,
       int         argc,
       char        **argv
   )
   {
           char *oid;
           OidMacro *om;
   
           if (argc != 3) {
                   fprintf( stderr, "%s: line %d: too many arguments\n",
                           fname, lineno );
   usage:  fprintf( stderr, "\tObjectIdentifier <name> <oid>\n");
                   return 1;
         }          }
         ldap_memfree(oc);  
           oid = find_oidm( argv[1] );
           if( oid != NULL ) {
                   fprintf( stderr,
                           "%s: line %d: "
                           "ObjectIdentifier \"%s\" previously defined \"%s\"",
                           fname, lineno, argv[1], oid );
                   return 1;
           }
   
           om = (OidMacro *) ch_malloc( sizeof(OidMacro) );
   
           om->som_names = NULL;
           charray_add( &om->som_names, argv[1] );
           om->som_oid.bv_val = find_oidm( argv[2] );
   
           if (!om->som_oid.bv_val) {
                   fprintf( stderr, "%s: line %d: OID %s not recognized\n",
                           fname, lineno, argv[2] );
                   goto usage;
           }
   
           if (om->som_oid.bv_val == argv[2]) {
                   om->som_oid.bv_val = ch_strdup( argv[2] );
           }
   
           om->som_oid.bv_len = strlen( om->som_oid.bv_val );
           om->som_next = om_list;
           om_list = om;
   
           return 0;
 }  }
   
 void  int
 parse_oc(  parse_oc(
     char        *fname,      const char  *fname,
     int         lineno,      int         lineno,
     char        *line      char        *line,
       char        **argv
 )  )
 {  {
         LDAP_OBJECT_CLASS *oc;          LDAPObjectClass *oc;
         int             code;          int             code;
         const char      *err;          const char      *err;
           char            *oid = NULL;
   
         oc = ldap_str2objectclass(line,&code,&err);          oc = ldap_str2objectclass(line,&code,&err,LDAP_SCHEMA_ALLOW_ALL);
         if ( !oc ) {          if ( !oc ) {
                 fprintf( stderr, "%s: line %d: %s before %s\n",                  fprintf( stderr, "%s: line %d: %s before %s\n",
                          fname, lineno, ldap_scherr2str(code), err );                           fname, lineno, ldap_scherr2str(code), err );
                 oc_usage();                  oc_usage();
                   return 1;
           }
   
           if ( oc->oc_oid == NULL ) {
                   fprintf( stderr,
                           "%s: line %d: objectclass has no OID\n",
                           fname, lineno );
                   oc_usage();
                   return 1;
           }
   
           if ( !OID_LEADCHAR( oc->oc_oid[0] )) {
                   /* Expand OID macros */
                   oid = find_oidm( oc->oc_oid );
                   if ( !oid ) {
                           fprintf( stderr,
                                   "%s: line %d: OID %s not recognized\n",
                                   fname, lineno, oc->oc_oid);
                           return 1;
                   }
                   if ( oid != oc->oc_oid ) {
                           ldap_memfree( oc->oc_oid );
                           oc->oc_oid = oid;
                   }
         }          }
   
         code = oc_add(oc,&err);          code = oc_add(oc,&err);
         if ( code ) {          if ( code ) {
                 fprintf( stderr, "%s: line %d: %s %s\n",                  fprintf( stderr, "%s: line %d: %s: \"%s\"\n",
                          fname, lineno, scherr2str(code), err);                           fname, lineno, scherr2str(code), err);
                 exit( 1 );                  return 1;
         }          }
   
         ldap_memfree(oc);          ldap_memfree(oc);
           return 0;
 }  }
   
 static void  static void
 oc_usage( void )  oc_usage( void )
 {  {
         fprintf( stderr, "ObjectClassDescription = \"(\" whsp\n");          fprintf( stderr,
         fprintf( stderr, "  numericoid whsp      ; ObjectClass identifier\n");                  "ObjectClassDescription = \"(\" whsp\n"
         fprintf( stderr, "  [ \"NAME\" qdescrs ]\n");                  "  numericoid whsp                 ; ObjectClass identifier\n"
         fprintf( stderr, "  [ \"DESC\" qdstring ]\n");                  "  [ \"NAME\" qdescrs ]\n"
         fprintf( stderr, "  [ \"OBSOLETE\" whsp ]\n");                  "  [ \"DESC\" qdstring ]\n"
         fprintf( stderr, "  [ \"SUP\" oids ]       ; Superior ObjectClasses\n");                  "  [ \"OBSOLETE\" whsp ]\n"
         fprintf( stderr, "  [ ( \"ABSTRACT\" / \"STRUCTURAL\" / \"AUXILIARY\" ) whsp ]\n");                  "  [ \"SUP\" oids ]                ; Superior ObjectClasses\n"
         fprintf( stderr, "                       ; default structural\n");                  "  [ ( \"ABSTRACT\" / \"STRUCTURAL\" / \"AUXILIARY\" ) whsp ]\n"
         fprintf( stderr, "  [ \"MUST\" oids ]      ; AttributeTypes\n");                  "                                  ; default structural\n"
         fprintf( stderr, "  [ \"MAY\" oids ]       ; AttributeTypes\n");                  "  [ \"MUST\" oids ]               ; AttributeTypes\n"
         fprintf( stderr, "whsp \")\"\n");                  "  [ \"MAY\" oids ]                ; AttributeTypes\n"
         exit( 1 );                  "  whsp \")\"\n" );
 }  }
   
 static void  
 oc_usage_old( void )  
 {  
         fprintf( stderr, "<oc clause> ::= objectclass <ocname>\n" );  
         fprintf( stderr, "                [ requires <attrlist> ]\n" );  
         fprintf( stderr, "                [ allows <attrlist> ]\n" );  
         exit( 1 );  
 }  
   
 static void  static void
 at_usage( void )  at_usage( void )
 {  {
         fprintf( stderr, "AttributeTypeDescription = \"(\" whsp\n");          fprintf( stderr,
         fprintf( stderr, "  numericoid whsp      ; AttributeType identifier\n");                  "AttributeTypeDescription = \"(\" whsp\n"
         fprintf( stderr, "  [ \"NAME\" qdescrs ]             ; name used in AttributeType\n");                  "  numericoid whsp      ; AttributeType identifier\n"
         fprintf( stderr, "  [ \"DESC\" qdstring ]            ; description\n");                  "  [ \"NAME\" qdescrs ]             ; name used in AttributeType\n"
         fprintf( stderr, "  [ \"OBSOLETE\" whsp ]\n");                  "  [ \"DESC\" qdstring ]            ; description\n"
         fprintf( stderr, "  [ \"SUP\" woid ]                 ; derived from this other\n");                  "  [ \"OBSOLETE\" whsp ]\n"
         fprintf( stderr, "                                 ; AttributeType\n");                  "  [ \"SUP\" woid ]                 ; derived from this other\n"
         fprintf( stderr, "  [ \"EQUALITY\" woid ]            ; Matching Rule name\n");                  "                                   ; AttributeType\n"
         fprintf( stderr, "  [ \"ORDERING\" woid ]            ; Matching Rule name\n");                  "  [ \"EQUALITY\" woid ]            ; Matching Rule name\n"
         fprintf( stderr, "  [ \"SUBSTR\" woid ]              ; Matching Rule name\n");                  "  [ \"ORDERING\" woid ]            ; Matching Rule name\n"
         fprintf( stderr, "  [ \"SYNTAX\" whsp noidlen whsp ] ; see section 4.3\n");                  "  [ \"SUBSTR\" woid ]              ; Matching Rule name\n"
         fprintf( stderr, "  [ \"SINGLE-VALUE\" whsp ]        ; default multi-valued\n");                  "  [ \"SYNTAX\" whsp noidlen whsp ] ; see section 4.3\n"
         fprintf( stderr, "  [ \"COLLECTIVE\" whsp ]          ; default not collective\n");                  "  [ \"SINGLE-VALUE\" whsp ]        ; default multi-valued\n"
         fprintf( stderr, "  [ \"NO-USER-MODIFICATION\" whsp ]; default user modifiable\n");                  "  [ \"COLLECTIVE\" whsp ]          ; default not collective\n"
         fprintf( stderr, "  [ \"USAGE\" whsp AttributeUsage ]; default userApplications\n");                  "  [ \"NO-USER-MODIFICATION\" whsp ]; default user modifiable\n"
         fprintf( stderr, "                                 ; userApplications\n");                  "  [ \"USAGE\" whsp AttributeUsage ]; default userApplications\n"
         fprintf( stderr, "                                 ; directoryOperation\n");                  "                                   ; userApplications\n"
         fprintf( stderr, "                                 ; distributedOperation\n");                  "                                   ; directoryOperation\n"
         fprintf( stderr, "                                 ; dSAOperation\n");                  "                                   ; distributedOperation\n"
         fprintf( stderr, "whsp \")\"\n");                  "                                   ; dSAOperation\n"
         exit( 1 );                  "  whsp \")\"\n");
 }  }
   
 void  int
 parse_at(  parse_at(
     char        *fname,      const char  *fname,
     int         lineno,      int         lineno,
     char        *line      char        *line,
       char        **argv
 )  )
 {  {
         LDAP_ATTRIBUTE_TYPE *at;          LDAPAttributeType *at;
         int             code;          int             code;
         const char      *err;          const char      *err;
           char            *oid = NULL;
           char            *soid = NULL;
   
         at = ldap_str2attributetype(line,&code,&err);          at = ldap_str2attributetype(line,&code,&err,LDAP_SCHEMA_ALLOW_ALL);
         if ( !at ) {          if ( !at ) {
                 fprintf( stderr, "%s: line %d: %s before %s\n",                  fprintf( stderr, "%s: line %d: %s before %s\n",
                          fname, lineno, ldap_scherr2str(code), err );                           fname, lineno, ldap_scherr2str(code), err );
                 at_usage();                  at_usage();
                   return 1;
           }
   
           if ( at->at_oid == NULL ) {
                   fprintf( stderr,
                           "%s: line %d: attributeType has no OID\n",
                           fname, lineno );
                   at_usage();
                   return 1;
           }
   
           if ( !OID_LEADCHAR( at->at_oid[0] )) {
                   /* Expand OID macros */
                   oid = find_oidm( at->at_oid );
                   if ( !oid ) {
                           fprintf( stderr,
                                   "%s: line %d: OID %s not recognized\n",
                                   fname, lineno, at->at_oid);
                           return 1;
                   }
                   if ( oid != at->at_oid ) {
                           ldap_memfree( at->at_oid );
                           at->at_oid = oid;
                   }
           }
   
           if ( at->at_syntax_oid && !OID_LEADCHAR( at->at_syntax_oid[0] )) {
                   /* Expand OID macros */
                   oid = find_oidm( at->at_syntax_oid );
                   if ( !oid ) {
                           fprintf(stderr,
                                   "%s: line %d: OID %s not recognized\n",
                                   fname, lineno, at->at_syntax_oid);
                           return 1;
                   }
                   if ( oid != at->at_syntax_oid ) {
                           ldap_memfree( at->at_syntax_oid );
                           at->at_syntax_oid = oid;
                   }
   
         }          }
         code = at_add(at,&err);          code = at_add(at,&err);
         if ( code ) {          if ( code ) {
                 fprintf( stderr, "%s: line %d: %s %s\n",                  fprintf( stderr, "%s: line %d: %s: \"%s\"\n",
                          fname, lineno, scherr2str(code), err);                           fname, lineno, scherr2str(code), err);
                 exit( 1 );                  return 1;
         }          }
         ldap_memfree(at);          ldap_memfree(at);
           return 0;
 }  }

Removed from v.1.12  
changed lines
  Added in v.1.12.8.14


______________
© Copyright 1998-2020, OpenLDAP Foundation, info@OpenLDAP.org