From 2012795d3b1a29913e9f3a5b3a35d40fd8f5f903 Mon Sep 17 00:00:00 2001 From: Howard Chu Date: Sun, 9 Apr 2017 02:21:06 +0100 Subject: [PATCH] Add config support for binary values Use base64 for .conf files, straight binary for back-config --- servers/slapd/bconfig.c | 13 ++++++++++++- servers/slapd/config.c | 34 ++++++++++++++++++++++++++++++++-- servers/slapd/config.h | 2 ++ 3 files changed, 46 insertions(+), 3 deletions(-) diff --git a/servers/slapd/bconfig.c b/servers/slapd/bconfig.c index f5b986b617..d9229864c1 100644 --- a/servers/slapd/bconfig.c +++ b/servers/slapd/bconfig.c @@ -4658,10 +4658,14 @@ check_vals( ConfigTable *ct, ConfigArgs *ca, void *ptr, int isAttr ) } for ( i=0; vals[i].bv_val; i++ ) { ca->line = vals[i].bv_val; + ca->linelen = vals[i].bv_len; if (( ad->ad_type->sat_flags & SLAP_AT_ORDERED_VAL ) && ca->line[0] == '{' ) { char *idx = strchr( ca->line, '}' ); - if ( idx ) ca->line = idx+1; + if ( idx ) { + ca->linelen -= (idx+1) - ca->line; + ca->line = idx+1; + } } rc = config_parse_vals( ct, ca, i ); if ( rc ) { @@ -5447,10 +5451,12 @@ config_add_internal( CfBackInfo *cfb, Entry *e, ConfigArgs *ca, SlapReply *rs, char *iptr = NULL; ca->valx = -1; ca->line = a->a_vals[i].bv_val; + ca->linelen = a->a_vals[i].bv_len; if ( a->a_desc->ad_type->sat_flags & SLAP_AT_ORDERED ) { ptr = strchr( ca->line, '}' ); if ( ptr ) { iptr = strchr( ca->line, '{' ); + ca->linelen -= (ptr+1) - ca->line; ca->line = ptr+1; } } @@ -5769,6 +5775,7 @@ config_modify_add( ConfigTable *ct, ConfigArgs *ca, AttributeDescription *ad, if ( next == ca->line + 1 || next[ 0 ] != '}' ) { return LDAP_OTHER; } + ca->linelen -= (ptr+1) - ca->line; ca->line = ptr+1; } } @@ -5990,6 +5997,7 @@ config_modify_internal( CfEntryInfo *ce, Operation *op, SlapReply *rs, bv.bv_val = ptr; } ca->line = bv.bv_val; + ca->linelen = bv.bv_len; ca->valx = d->idx[i]; config_parse_vals(ct, ca, d->idx[i] ); rc = config_del_vals( ct, ca ); @@ -6028,6 +6036,7 @@ config_modify_internal( CfEntryInfo *ce, Operation *op, SlapReply *rs, break; for (i=0; ml->sml_values[i].bv_val; i++) { ca->line = ml->sml_values[i].bv_val; + ca->linelen = ml->sml_values[i].bv_len; ca->valx = -1; rc = config_modify_add( ct, ca, ml->sml_desc, i ); if ( rc ) @@ -6057,6 +6066,7 @@ out: } for ( i=0; !BER_BVISNULL( &s->a_vals[i] ); i++ ) { ca->line = s->a_vals[i].bv_val; + ca->linelen = s->a_vals[i].bv_len; ca->valx = -1; config_modify_add( ct, ca, s->a_desc, i ); } @@ -6074,6 +6084,7 @@ out: s->a_flags &= ~(SLAP_ATTR_IXDEL|SLAP_ATTR_IXADD); for ( i=0; !BER_BVISNULL( &s->a_vals[i] ); i++ ) { ca->line = s->a_vals[i].bv_val; + ca->linelen = s->a_vals[i].bv_len; ca->valx = -1; config_modify_add( ct, ca, s->a_desc, i ); } diff --git a/servers/slapd/config.c b/servers/slapd/config.c index 023b23e11e..5846ea59a5 100644 --- a/servers/slapd/config.c +++ b/servers/slapd/config.c @@ -126,6 +126,19 @@ ConfigTable *config_find_keyword(ConfigTable *Conf, ConfigArgs *c) { if( (Conf[i].length && (!strncasecmp(c->argv[0], Conf[i].name, Conf[i].length))) || (!strcasecmp(c->argv[0], Conf[i].name)) ) break; if ( !Conf[i].name ) return NULL; + if (( Conf[i].arg_type & ARGS_TYPES ) == ARG_BINARY ) { + size_t decode_len = LUTIL_BASE64_DECODE_LEN(c->linelen); + ch_free( c->tline ); + c->tline = ch_malloc( decode_len+1 ); + c->linelen = lutil_b64_pton( c->line, c->tline, decode_len ); + if ( c->linelen < 0 ) + { + ch_free( c->tline ); + c->tline = NULL; + return NULL; + } + c->line = c->tline; + } return Conf+i; } @@ -210,6 +223,13 @@ int config_check_vals(ConfigTable *Conf, ConfigArgs *c, int check_only ) { assert( c->argc == 2 ); if ( !check_only ) ber_str2bv( c->argv[1], 0, 1, &c->value_bv ); + } else if(arg_type == ARG_BINARY) { + assert( c->argc == 2 ); + if ( !check_only ) { + c->value_bv.bv_len = c->linelen; + c->value_bv.bv_val = ch_malloc( c->linelen ); + AC_MEMCPY( c->value_bv.bv_val, c->line, c->linelen ); + } } else if(arg_type == ARG_DN) { struct berval bv; assert( c->argc == 2 ); @@ -403,6 +423,7 @@ int config_set_vals(ConfigTable *Conf, ConfigArgs *c) { break; } case ARG_BERVAL: + case ARG_BINARY: *(struct berval *)ptr = c->value_bv; break; case ARG_ATDESC: @@ -551,6 +572,10 @@ init_config_attrs(ConfigTable *ct) { fprintf( stderr, "init_config_attrs: register_at failed\n" ); return code; } + if (( ct[i].arg_type & ARGS_TYPES ) == ARG_BINARY ) { + ldif_must_b64_encode_register( ct[i].ad->ad_cname.bv_val, + ct[i].ad->ad_type->sat_oid ); + } } return 0; @@ -651,13 +676,15 @@ int config_parse_vals(ConfigTable *ct, ConfigArgs *c, int valx) { int rc = 0; + int arg_type = ct->arg_type & ARGS_TYPES; snprintf( c->log, sizeof( c->log ), "%s: value #%d", ct->ad->ad_cname.bv_val, valx ); c->argc = 1; c->argv[0] = ct->ad->ad_cname.bv_val; - if ( ( ct->arg_type & ARG_QUOTE ) && c->line[ 0 ] != '"' ) { + if ( (( ct->arg_type & ARG_QUOTE ) && c->line[ 0 ] != '"' ) || + (arg_type == ARG_BERVAL || arg_type == ARG_BINARY)) { c->argv[c->argc] = c->line; c->argc++; c->argv[c->argc] = NULL; @@ -679,13 +706,15 @@ int config_parse_add(ConfigTable *ct, ConfigArgs *c, int valx) { int rc = 0; + int arg_type = ct->arg_type & ARGS_TYPES; snprintf( c->log, sizeof( c->log ), "%s: value #%d", ct->ad->ad_cname.bv_val, valx ); c->argc = 1; c->argv[0] = ct->ad->ad_cname.bv_val; - if ( ( ct->arg_type & ARG_QUOTE ) && c->line[ 0 ] != '"' ) { + if ( (( ct->arg_type & ARG_QUOTE ) && c->line[ 0 ] != '"' ) || + (arg_type == ARG_BERVAL || arg_type == ARG_BINARY)) { c->argv[c->argc] = c->line; c->argc++; c->argv[c->argc] = NULL; @@ -2276,6 +2305,7 @@ config_fp_parse_line(ConfigArgs *c) int inquote = 0; c->tline = ch_strdup(c->line); + c->linelen = strlen(c->line); token = strtok_quote(c->tline, " \t", "e_ptr, &inquote); if(token) for(i = 0; hide[i]; i++) if(!strcasecmp(token, hide[i])) break; diff --git a/servers/slapd/config.h b/servers/slapd/config.h index 2d19901731..f33881c446 100644 --- a/servers/slapd/config.h +++ b/servers/slapd/config.h @@ -60,6 +60,7 @@ typedef enum { #define ARG_UINT 0x00008000 #define ARG_ATDESC 0x00009000 #define ARG_ULONG 0x0000a000 +#define ARG_BINARY 0x0000b000 #define ARGS_SYNTAX 0xffff0000 #define ARG_IGNORED 0x00080000 @@ -134,6 +135,7 @@ typedef struct config_args_s { char *tline; const char *fname; int lineno; + int linelen; char log[MAXPATHLEN + STRLENOF(": line ") + LDAP_PVT_INTTYPE_CHARS(unsigned long)]; #define cr_msg reply.msg ConfigReply reply; -- 2.39.5