4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License, Version 1.0 only
6 * (the "License"). You may not use this file except in compliance
9 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
10 * or http://www.opensolaris.org/os/licensing.
11 * See the License for the specific language governing permissions
12 * and limitations under the License.
14 * When distributing Covered Code, include this CDDL HEADER in each
15 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
16 * If applicable, add the following below this CDDL HEADER, with the
17 * fields enclosed by brackets "[]" replaced with your own identifying
18 * information: Portions Copyright [yyyy] [name of copyright owner]
23 * Copyright 2015 Gary Mills
24 * Copyright 2005 Sun Microsystems, Inc. All rights reserved.
25 * Use is subject to license terms.
36 #include "ldap_parse.h"
37 #include "nis_parse_ldap_conf.h"
38 #include "nis_parse_ldap_util.h"
39 #include "ldap_util.h"
41 /* Forward declarations */
42 int getfullmapname(char **, const char *);
43 int checkfullmapname(const char *, const char *, __nis_table_mapping_t
**,
44 __nis_table_mapping_t
**);
45 int append_domainContext(__nis_table_mapping_t
**, char *, char *);
47 static int merge_table_mapping(__nis_table_mapping_t
*in
,
48 __nis_table_mapping_t
*out
);
49 __nis_table_mapping_t
*new_merged_mapping(const char *,
50 __nis_table_mapping_t
*intbl
);
51 static int append_mapping_rule(__nis_mapping_rule_t
*src_rule
,
52 __nis_table_mapping_t
*tbl
, int flag
);
55 static int copy_object_dn(__nis_object_dn_t
*in
,
56 __nis_object_dn_t
*newdn
);
59 * FUNCTION: initialize_table_mapping
61 * Initialize the __nis_table_mapping_t structure.
63 * INPUT: __nis_table_mapping_t
67 initialize_table_mapping(
68 __nis_table_mapping_t
*mapping
)
70 if (mapping
!= NULL
) {
73 mapping
->index
.numIndexes
= 0;
74 mapping
->index
.name
= NULL
;
75 mapping
->index
.value
= NULL
;
77 mapping
->numColumns
= 0;
78 mapping
->column
= NULL
;
80 mapping
->initTtlLo
= (time_t)NO_VALUE_SET
;
81 mapping
->initTtlHi
= (time_t)NO_VALUE_SET
;
82 mapping
->ttl
= (time_t)NO_VALUE_SET
;
84 mapping
->usedns_flag
= 0;
85 mapping
->securemap_flag
= 0;
86 mapping
->commentChar
= DEFAULT_COMMENT_CHAR
;
87 mapping
->numSplits
= 0;
89 mapping
->objectDN
= NULL
;
91 mapping
->separatorStr
= DEFAULT_SEP_STRING
;
93 mapping
->numRulesFromLDAP
= 0;
94 mapping
->numRulesToLDAP
= 0;
96 mapping
->ruleFromLDAP
= NULL
;
97 mapping
->ruleToLDAP
= NULL
;
100 mapping
->objName
= NULL
;
101 mapping
->objPath
= NULL
;
103 mapping
->isMaster
= 0;
104 mapping
->seq_num
= NO_VALUE_SET
;
109 * FUNCTION: initialize_yp_parse_structs
111 * Initialize the __yp_domain_context_t structure.
113 * INPUT: __yp_domain_context_t
117 initialize_yp_parse_structs(
118 __yp_domain_context_t
*ypDomains
)
120 ypDomains
->numDomains
= 0;
121 ypDomains
->domainLabels
= NULL
;
122 ypDomains
->domains
= NULL
;
123 ypDomains
->numYppasswdd
= 0;
124 ypDomains
->yppasswddDomainLabels
= NULL
;
128 * FUNCTION: merge_table_mapping
130 * Merges information from one table_mapping struct
133 * INPUT: Source and Destination table_mapping structs.
134 * RETURN: 0 on success and > 0 on error.
139 __nis_table_mapping_t
*in
,
140 __nis_table_mapping_t
*out
)
149 if (in
->dbId
== NULL
)
153 * If 'in' is generic (non-expanded) and 'out' is domain-specific,
154 * then rules from 'in' should not be appended to those in 'out'.
156 if (!strchr(in
->dbId
, COMMA_CHAR
) && strchr(out
->dbId
, COMMA_CHAR
))
162 if (!out
->index
.numIndexes
&& in
->index
.numIndexes
> 0) {
163 if (!dup_index(&in
->index
, &out
->index
))
167 /* add_column() increments numColumns, so we don't */
168 if (!out
->numColumns
&& in
->numColumns
> 0) {
169 for (i
= 0; i
< in
->numColumns
; i
++) {
170 if (!add_column(out
, in
->column
[i
]))
175 if (out
->commentChar
== DEFAULT_COMMENT_CHAR
&&
176 in
->commentChar
!= DEFAULT_COMMENT_CHAR
)
177 out
->commentChar
= in
->commentChar
;
179 if (out
->usedns_flag
== 0)
180 out
->usedns_flag
= in
->usedns_flag
;
182 if (out
->securemap_flag
== 0)
183 out
->securemap_flag
= in
->securemap_flag
;
185 if ((strcmp(out
->separatorStr
, DEFAULT_SEP_STRING
) == 0) &&
186 (strcmp(in
->separatorStr
, DEFAULT_SEP_STRING
) != 0)) {
187 out
->separatorStr
= s_strdup(in
->separatorStr
);
188 if (!out
->separatorStr
)
192 if (!out
->numSplits
&& !out
->e
&& in
->e
) {
193 out
->numSplits
= in
->numSplits
;
194 out
->e
= (__nis_mapping_element_t
*)
195 s_calloc(1, (in
->numSplits
+1) *
196 sizeof (__nis_mapping_element_t
));
199 for (i
= 0; i
<= in
->numSplits
; i
++) {
200 if (!dup_mapping_element(&in
->e
[i
], &out
->e
[i
])) {
202 free_mapping_element(&out
->e
[i
- 1]);
210 if (out
->initTtlLo
== (time_t)NO_VALUE_SET
&&
211 in
->initTtlLo
!= (time_t)NO_VALUE_SET
)
212 out
->initTtlLo
= in
->initTtlLo
;
214 if (out
->initTtlHi
== (time_t)NO_VALUE_SET
&&
215 in
->initTtlHi
!= (time_t)NO_VALUE_SET
)
216 out
->initTtlHi
= in
->initTtlHi
;
218 if (out
->ttl
== (time_t)NO_VALUE_SET
&&
219 in
->ttl
!= (time_t)NO_VALUE_SET
)
222 if (!out
->numRulesFromLDAP
&& in
->numRulesFromLDAP
) {
223 out
->ruleFromLDAP
= dup_mapping_rules(in
->ruleFromLDAP
,
224 in
->numRulesFromLDAP
);
225 if (!out
->ruleFromLDAP
)
227 out
->numRulesFromLDAP
= in
->numRulesFromLDAP
;
228 } else if (append
&& out
->numRulesFromLDAP
&& in
->numRulesFromLDAP
) {
229 orig_num_rules
= out
->numRulesFromLDAP
;
230 for (i
= 0; i
< in
->numRulesFromLDAP
; i
++) {
231 if (append_mapping_rule(in
->ruleFromLDAP
[i
], out
, 0)) {
232 for (i
= out
->numRulesFromLDAP
;
233 i
> orig_num_rules
; i
--) {
234 free_mapping_rule(out
->ruleFromLDAP
[i
]);
235 out
->ruleFromLDAP
[i
] = NULL
;
243 if (!out
->numRulesToLDAP
&& in
->numRulesToLDAP
) {
244 out
->ruleToLDAP
= dup_mapping_rules(in
->ruleToLDAP
,
246 if (!out
->ruleToLDAP
)
248 out
->numRulesToLDAP
= in
->numRulesToLDAP
;
249 } else if (append
&& out
->numRulesToLDAP
&& in
->numRulesToLDAP
) {
250 orig_num_rules
= out
->numRulesToLDAP
;
251 for (i
= 0; i
< in
->numRulesToLDAP
; i
++) {
252 if (append_mapping_rule(in
->ruleToLDAP
[i
], out
, 1)) {
253 for (i
= out
->numRulesToLDAP
;
254 i
> orig_num_rules
; i
--) {
255 free_mapping_rule(out
->ruleToLDAP
[i
]);
256 out
->ruleToLDAP
[i
] = NULL
;
262 if (!out
->objectDN
&& in
->objectDN
) {
263 out
->objectDN
= (__nis_object_dn_t
*)
264 s_calloc(1, sizeof (__nis_object_dn_t
));
267 if (copy_object_dn(in
->objectDN
, out
->objectDN
)) {
268 free_object_dn(out
->objectDN
);
269 out
->objectDN
= NULL
;
274 if (!out
->objName
&& in
->objName
) {
275 if (!strchr(in
->objName
, SPACE_CHAR
)) {
276 /* objName has no space- a single map dbIdMapping */
277 out
->objName
= s_strndup(in
->objName
,
278 strlen(in
->objName
));
284 if (!out
->objName
&& out
->dbId
) {
285 out
->objName
= s_strndup(out
->dbId
, strlen(out
->dbId
));
290 if (out
->seq_num
== NO_VALUE_SET
&& in
->seq_num
>= 0)
291 out
->seq_num
= in
->seq_num
;
293 return (p_error
== no_parse_error
? 0 : 1);
297 * FUNCTION: copy_object_dn
299 * Copies a __nis_object_dn_t structure.
301 * RETURN: 0 on success, > 0 on failure.
303 * NOTE: The caller MUST free newdn using
304 * free_object_dn() if return value != 0 (error condition)
308 copy_object_dn(__nis_object_dn_t
*in
, __nis_object_dn_t
*newdn
)
311 p_error
= parse_no_object_dn
;
315 if (in
->read
.base
== NULL
) {
316 newdn
->read
.base
= NULL
;
318 newdn
->read
.base
= s_strndup(
319 in
->read
.base
, strlen(in
->read
.base
));
320 if (newdn
->read
.base
== NULL
)
323 newdn
->read
.scope
= in
->read
.scope
;
324 if (in
->read
.attrs
) {
325 newdn
->read
.attrs
= s_strndup(
326 in
->read
.attrs
, strlen(in
->read
.attrs
));
327 if (newdn
->read
.attrs
== NULL
) {
331 newdn
->read
.attrs
= NULL
;
333 newdn
->read
.element
= in
->read
.element
;
334 if (in
->write
.base
!= NULL
) {
335 newdn
->write
.base
= s_strndup(
336 in
->write
.base
, strlen(in
->write
.base
));
337 if (newdn
->write
.base
== NULL
)
340 newdn
->write
.base
= NULL
;
342 newdn
->write
.scope
= in
->write
.scope
;
343 if (in
->write
.attrs
!= NULL
) {
344 newdn
->write
.attrs
= s_strndup(
345 in
->write
.attrs
, strlen(in
->write
.attrs
));
346 if (newdn
->write
.attrs
== NULL
) {
350 newdn
->write
.attrs
= NULL
;
352 newdn
->write
.element
= in
->write
.element
;
354 newdn
->dbIdName
= s_strndup(in
->dbIdName
,
355 strlen(in
->dbIdName
));
356 if (newdn
->dbIdName
== NULL
)
361 newdn
->delDisp
= in
->delDisp
;
363 if (in
->dbId
&& in
->numDbIds
> 0) {
364 newdn
->dbId
= dup_mapping_rules(in
->dbId
,
368 newdn
->numDbIds
= in
->numDbIds
;
370 if (in
->next
!= NULL
) {
371 newdn
->next
= (__nis_object_dn_t
*)s_calloc(1,
372 sizeof (__nis_object_dn_t
));
373 if (newdn
->next
== NULL
)
380 } /* End of while on in */
386 * FUNCTION: free_yp_domain_context
388 * Frees __yp_domain_context_t
390 * INPUT: __yp_domain_context_t
393 free_yp_domain_context(__yp_domain_context_t
*domains
)
397 if (domains
!= NULL
) {
398 for (i
= 0; i
< domains
->numDomains
; i
++) {
399 if (domains
->domains
[i
] != NULL
) {
400 free(domains
->domains
[i
]);
401 domains
->domains
[i
] = NULL
;
403 if (domains
->domainLabels
[i
] != NULL
) {
404 free(domains
->domainLabels
[i
]);
405 domains
->domainLabels
[i
] = NULL
;
408 domains
->domains
= NULL
;
409 domains
->domainLabels
= NULL
;
410 for (i
= 0; i
< domains
->numYppasswdd
; i
++) {
411 if (domains
->yppasswddDomainLabels
[i
] != NULL
) {
412 free(domains
->yppasswddDomainLabels
[i
]);
413 domains
->yppasswddDomainLabels
[i
] =
417 domains
->yppasswddDomainLabels
= NULL
;
418 domains
->numDomains
= 0;
424 * FUNCTION: second_parser_pass
426 * Prepares the linked list of table_mappings for processing
427 * by finish_parse(), adding, merging and deleting structures
428 * as necessary. Also adds dummy objectDN info. for splitField's.
430 * RETURN VALUE: 0 on success, > 0 on failure.
433 second_parser_pass(__nis_table_mapping_t
**table_mapping
)
435 __nis_table_mapping_t
*t
, *t2
;
436 __nis_table_mapping_t
*t_new
= NULL
, *tg
;
437 __nis_table_mapping_t
*prev
= NULL
;
439 char *objName
= NULL
;
441 char *tobj
, *alias
, *dupalias
, *tmp
;
442 char *myself
= "second_parser_pass";
446 for (t
= *table_mapping
; t
!= NULL
; ) {
448 * Temporarily using this field to flag deletion.
451 * The mapping structure will be deleted in final_parser_pass
456 p_error
= parse_bad_map_error
;
457 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
458 "%s: no dbId field", myself
);
462 dom
= strchr(t
->dbId
, COMMA_CHAR
);
463 if (t
->objName
!= NULL
) {
464 objName
= strdup(t
->objName
);
465 if (objName
== NULL
) {
466 p_error
= parse_no_mem_error
;
467 logmsg(MSG_NOMEM
, LOG_ERR
,
468 "%s: Cannot allocate memory for objName",
472 objs
= (char *)strtok_r(objName
, " ", &lasts
);
473 /* Get the generic mapping */
475 tg
= find_table_mapping(t
->dbId
, dom
- t
->dbId
,
481 t
->objName
= s_strndup(t
->dbId
,
484 logmsg(MSG_NOMEM
, LOG_ERR
,
485 "%s: Cannot allocate memory for "
486 "t->objName", myself
);
491 /* Force relationship for domain specific */
493 /* Get the generic mapping */
494 tg
= find_table_mapping(t
->dbId
, dom
- t
->dbId
,
496 if (tg
== NULL
|| tg
->objName
== NULL
) {
497 /* If not found, use dbId for objName */
498 t
->objName
= s_strndup(t
->dbId
,
500 if (t
->objName
== NULL
) {
501 logmsg(MSG_NOMEM
, LOG_ERR
,
502 "%s: Cannot allocate memory for t->objName",
508 tobj
= s_strndup(tg
->objName
,
509 strlen(tg
->objName
));
511 logmsg(MSG_NOMEM
, LOG_ERR
,
512 "%s: Cannot allocate memory for t->objName",
516 alias
= (char *)strtok_r(tobj
, " ",
519 /* Loop 'breaks' on errors */
522 dupalias
= s_strndup(alias
,
526 if (getfullmapname(&dupalias
,
531 if (t
->objName
== NULL
)
532 t
->objName
= dupalias
;
534 len
= strlen(t
->objName
)
537 tmp
= s_calloc(1, len
);
549 alias
= (char *)strtok_r(NULL
,
556 (objName
= s_strdup(t
->objName
))
559 logmsg(MSG_NOTIMECHECK
,
561 "%s: getfullmapname failed for %s for domain \"%s\"",
569 "%s: Cannot allocate memory",
577 objs
= (char *)strtok_r(objName
, " ",
584 if (merge_table_mapping(tg
, t
)) {
585 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
586 "Error merging information from the %s to the %s mapping structure",
595 * If objName is "map1 map2" then do the second pass.
596 * If it is just "map1" however skip the expansion.
597 * Also skip it if t->objName is null.
599 if (objs
&& strncasecmp(objs
, t
->objName
,
600 strlen(t
->objName
))) {
601 t2
= find_table_mapping(objs
, strlen(objs
),
604 if (merge_table_mapping(t
, t2
)) {
605 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
606 "Error merging information from the %s to the %s mapping structure",
614 t_new
= new_merged_mapping(objs
, t
);
620 *table_mapping
= t_new
;
624 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
625 "Error creating a new mapping structure %s",
632 while ((objs
= (char *)strtok_r(NULL
, " ", &lasts
))
634 t2
= find_table_mapping(objs
, strlen(objs
),
637 if (merge_table_mapping(t
, t2
)) {
638 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
639 "Error merging information from the %s to the %s mapping structure",
648 * create a new t_map with dbId = objs
649 * and copy t->* into new t_map
651 t_new
= new_merged_mapping(objs
, t
);
657 *table_mapping
= t_new
;
661 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
662 "Error creating a new mapping structure %s",
670 } /* if objs!= NULL */
680 } /* for t = table_mapping loop */
684 __nis_table_mapping_t
*
685 new_merged_mapping(const char *match
,
686 __nis_table_mapping_t
*intbl
)
689 __nis_table_mapping_t
*outtable
= NULL
;
691 outtable
= (__nis_table_mapping_t
*)
692 s_calloc(1, sizeof (__nis_table_mapping_t
));
693 if (outtable
== NULL
)
695 initialize_table_mapping(outtable
);
696 outtable
->dbId
= s_strndup(match
, strlen(match
));
697 if (outtable
->dbId
== NULL
) {
698 free_table_mapping(outtable
);
702 if (merge_table_mapping(intbl
, outtable
)) {
703 free_table_mapping(outtable
);
710 * FUNCTION: final_parser_pass
712 * completes the final expansion of t_map structures linked list.
713 * all structures will have a non-null objPath as well as a objName
714 * in the form of "mapname . domainname ." or "splitfieldname .
717 * RETURN VALUE: 0 on success, -1 on failure, -2 on fatal error.
721 __nis_table_mapping_t
**table_mapping
,
722 __yp_domain_context_t
*ypDomains
)
724 __nis_table_mapping_t
*t
;
725 __nis_table_mapping_t
*t1
, *returned_map
;
726 __nis_table_mapping_t
*prev
= NULL
;
728 char *myself
= "final_parser_pass";
731 int del_tbl_flag
= 0;
734 if (!ypDomains
->numDomains
) {
735 p_error
= parse_internal_error
;
736 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
737 "%s:No domains specified.", myself
);
741 p_error
= parse_internal_error
;
742 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
743 "%s:No domain structure supplied.", myself
);
748 for (t
= *table_mapping
; t
!= NULL
; ) {
750 /* Delete if marked for deletion by second_parser_pass */
751 if (t
->isMaster
== 1) {
753 prev
->next
= t
->next
;
755 *table_mapping
= t
->next
;
758 free_table_mapping(t1
);
762 if (!t
->objName
&& t
->dbId
) {
763 t
->objName
= s_strndup(t
->dbId
, strlen(t
->dbId
));
765 logmsg(MSG_NOMEM
, LOG_ERR
,
766 "%s:Could not allocate.", myself
);
770 i
= ypDomains
->numDomains
;
773 /* modify existing table_mapping's */
774 nm
= checkfullmapname(t
->dbId
,
775 ypDomains
->domainLabels
[0],
776 table_mapping
, &returned_map
);
778 /* delete this mapping structure */
779 logmsg(MSG_NOTIMECHECK
,
781 "Mapping structure %s,%s "
784 ypDomains
->domainLabels
[0]);
785 if (merge_table_mapping(t
,
787 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
788 "Error merging information "
789 "from the %s to the %s "
790 "mapping structure.",
795 if (del_tbl_flag
== 0)
797 } else if (nm
== -1) {
798 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
799 "Error searching for %s,%s structure",
801 ypDomains
->domainLabels
[0]);
803 } else if (nm
== 0 || nm
== 2) {
804 if ((append_domainContext(&t
,
805 ypDomains
->domainLabels
[0],
806 ypDomains
->domains
[0])) != 0) {
807 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
808 "Error appending domainContext %s",
809 ypDomains
->domainLabels
[0]);
814 } else { /* if (i > 1) */
815 /* need to create new table_mapping's */
816 nm
= checkfullmapname(t
->dbId
,
817 ypDomains
->domainLabels
[i
- 1],
818 table_mapping
, &returned_map
);
820 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
821 "Error searching for %s,%s structure",
823 ypDomains
->domainLabels
[i
- 1]);
825 } else if (nm
== 0) {
826 t1
= new_merged_mapping(t
->dbId
, t
);
827 /* we clone ourselves */
829 if ((append_domainContext(&t1
,
830 ypDomains
->domainLabels
[i
- 1],
831 ypDomains
->domains
[i
- 1])) != 0) {
832 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
833 "Error appending domainContext %s",
834 ypDomains
->domainLabels
[i
- 1]);
839 t1
->next
= prev
->next
;
848 } else { /* if !t1 */
849 p_error
= parse_internal_error
;
850 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
851 "%s:Could not create new table -"
852 " check all instances of %s for errors",
856 } else if (nm
== 1) {
857 logmsg(MSG_NOTIMECHECK
, LOG_WARNING
,
858 "Mapping structure %s,%s already exists.",
860 ypDomains
->domainLabels
[i
- 1]);
862 * We should be deleting this, but can't
863 * really do it here, because we need to
864 * match with the domainLabels[0] case
865 * too. So we will just flag it for now.
867 if (merge_table_mapping(t
,
869 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
870 "Error merging information from the %s to the %s mapping structure.",
876 } else if (nm
== 2) {
877 if ((append_domainContext(&t
,
878 ypDomains
->domainLabels
[i
- 1],
879 ypDomains
->domains
[i
- 1])) != 0) {
880 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
881 "Error appending domainContext %s",
882 ypDomains
->domainLabels
[i
- 1]);
885 } /* end of "if (nm == 0)" */
886 } /* end of else if (i > 1) */
890 * 'merge_table_mapping' only copies unexpanded
891 * objectDN values into returned_map. Hence,
892 * read.base and write.base in returned_map
893 * needs to be expanded.
895 if (nm
== 1 && returned_map
&& returned_map
->objectDN
) {
897 returned_map
->objectDN
,
898 ypDomains
->domains
[i
- 1]);
900 returned_map
->objectDN
->write
.base
) {
902 &returned_map
->objectDN
->write
.base
,
903 ypDomains
->domains
[i
- 1]);
907 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
908 "Error appending domainContext "
910 ypDomains
->domainLabels
[i
- 1],
916 } /* end of while i > 0 loop */
918 if (del_tbl_flag
== 1) {
920 prev
->next
= t
->next
;
921 free_table_mapping(t
);
924 *table_mapping
= t
->next
;
925 free_table_mapping(t
);
933 } /* end of table mapping loop */
935 for (t
= *table_mapping
; t
!= NULL
; t
= t
->next
) {
937 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
938 "%s:Fatal error: structure with no dbId found.",
942 append_dot(&t
->dbId
);
944 p_error
= parse_internal_error
;
945 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
946 "%s:No objectDN for %s.", myself
, t
->dbId
);
955 * FUNCTION: append_mapping_rule
957 * Appends mapping rules to a table_mapping structure
958 * with previously existing rules. flag controls whether
959 * the functions works on the rules From or To LDAP.
961 * RETURN VALUE: 0 on success, >= 1 on failure.
965 append_mapping_rule(__nis_mapping_rule_t
*src_rule
,
966 __nis_table_mapping_t
*dst
, int flag
)
968 __nis_mapping_rule_t
**rules
= NULL
;
971 if (dst
->ruleFromLDAP
== NULL
) {
972 p_error
= parse_internal_error
;
975 rules
= (__nis_mapping_rule_t
**)
976 s_realloc(dst
->ruleFromLDAP
,
977 (dst
->numRulesFromLDAP
+ 1) *
978 sizeof (__nis_mapping_rule_t
*));
981 dst
->ruleFromLDAP
= rules
;
982 rules
[dst
->numRulesFromLDAP
] = dup_mapping_rule(src_rule
);
983 if (rules
[dst
->numRulesFromLDAP
] == NULL
) {
984 p_error
= parse_no_mem_error
;
987 dst
->numRulesFromLDAP
++;
988 } else if (flag
== 1) {
989 if (dst
->ruleToLDAP
== NULL
) {
990 p_error
= parse_internal_error
;
993 rules
= (__nis_mapping_rule_t
**)
994 s_realloc(dst
->ruleToLDAP
,
995 (dst
->numRulesToLDAP
+ 1) *
996 sizeof (__nis_mapping_rule_t
*));
999 dst
->ruleToLDAP
= rules
;
1000 rules
[dst
->numRulesToLDAP
] = dup_mapping_rule(src_rule
);
1001 if (rules
[dst
->numRulesToLDAP
] == NULL
) {
1002 p_error
= parse_no_mem_error
;
1005 dst
->numRulesToLDAP
++;
1013 * FUNCTION: check_domain_specific_order
1015 * Makes sure that an attribute with explicitly specified
1016 * nisLDAPdomainContext is found before its non-domain
1017 * specific counterpart.
1019 * RETURN VALUE: 0 normal exit
1020 * 1 if domain specific attribute found
1021 * after non-domain specific one.
1022 * -1 some error condition
1026 check_domain_specific_order(const char *sd
,
1027 config_key attrib_num
,
1028 __nis_table_mapping_t
*table_mapping
,
1029 __yp_domain_context_t
*ypDomains
)
1031 __nis_table_mapping_t
*t
;
1032 char *myself
= "check_domain_specific_order";
1039 if (!ypDomains
->numDomains
) {
1040 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
1041 "%s:No domains specified.", myself
);
1045 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
1046 "%s:No domain structure supplied.", myself
);
1050 for (i
= 0; i
< ypDomains
->numDomains
; i
++) {
1051 for (t
= table_mapping
; t
!= NULL
; t
= t
->next
) {
1053 if ((strcasecmp(t
->dbId
, sd
) == 0) && (len
==
1055 /* prevent from matching against itself */
1057 dbId
= s_strndup(t
->dbId
, strlen(t
->dbId
));
1059 logmsg(MSG_NOMEM
, LOG_ERR
,
1060 "%s:Memory allocation error.", myself
);
1064 if (getfullmapname(&dbId
,
1065 ypDomains
->domainLabels
[i
])) {
1066 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
1067 "Error getting fully qualified name for %s",
1072 if ((strcasecmp(dbId
, sd
) == 0) && (len
==
1075 switch (attrib_num
) {
1076 case key_yp_map_flags
:
1077 if (t
->usedns_flag
!= 0 ||
1078 t
->securemap_flag
!= 0)
1080 type
= YP_MAP_FLAGS
;
1082 case key_yp_comment_char
:
1083 if (t
->commentChar
!=
1084 DEFAULT_COMMENT_CHAR
)
1086 type
= YP_COMMENT_CHAR
;
1088 case key_yp_repeated_field_separators
:
1089 if (strcmp(t
->separatorStr
,
1090 DEFAULT_SEP_STRING
) != 0)
1093 YP_REPEATED_FIELD_SEPARATORS
;
1095 case key_yp_name_fields
:
1096 if (t
->e
&& t
->numColumns
)
1098 type
= YP_NAME_FIELDS
;
1099 case key_yp_split_field
:
1100 if (t
->e
&& t
->numColumns
)
1102 type
= YP_SPLIT_FIELD
;
1104 case key_yp_db_id_map
:
1107 type
= YP_DB_ID_MAP
;
1109 case key_yp_entry_ttl
:
1111 (time_t)NO_VALUE_SET
)
1113 type
= YP_ENTRY_TTL
;
1115 case key_yp_ldap_object_dn
:
1118 type
= YP_LDAP_OBJECT_DN
;
1120 case key_nis_to_ldap_map
:
1123 type
= NIS_TO_LDAP_MAP
;
1125 case key_ldap_to_nis_map
:
1126 if (t
->ruleFromLDAP
)
1128 type
= LDAP_TO_NIS_MAP
;
1134 } /* end of switch */
1136 logmsg(MSG_NOTIMECHECK
, LOG_ERR
,
1137 "Relative attribute '%s' of type '%s' found before fully qualified one '%s'",
1143 } /* end of strncasecmp */
1146 } /* end of t loop */
1147 } /* end of i loop */
1154 getfullmapname(char **mapname
, const char *domainname
)
1156 char *maps
= *mapname
;
1157 int maplen
= strlen(maps
);
1158 int domainlen
= strlen(domainname
);
1160 if (!maplen
|| !domainlen
||
1161 maps
[maplen
- 1] == PERIOD_CHAR
)
1163 else if (strchr(maps
, COMMA_CHAR
)) {
1164 /* map already has a domain part, do nothing */
1167 append_comma(&maps
);
1168 maplen
= strlen(maps
);
1169 maps
= realloc(maps
, (maplen
+ domainlen
+ 1));
1171 if (strlcat(maps
, domainname
, (maplen
+ domainlen
+ 1))
1172 >= (maplen
+ domainlen
+ 1))
1182 * FUNCTION: checkfullmapname
1184 * Tries to find out if by appending the table mapping structures
1185 * with each of the provided nisLDAPdomainContexts, an already
1186 * existing fqdn table mapping structure results. That would be the
1187 * case when a full qualified domain specific attribute was present.
1189 * Note that per NISLDAPmapping(4) such an attribute MUST be listed
1190 * in the mapping file BEFORE its non-fqdn counterpart.
1192 * RETURNS: 0 normal exit, 1 if an existing structure found, -1 for all
1193 * errors, 2 if already fqdn. If returning 1 the existing structure is
1198 checkfullmapname(const char *mapname
, const char *domainname
,
1199 __nis_table_mapping_t
**table_mapping
,
1200 __nis_table_mapping_t
**found_map
)
1206 /* This function does not alter mapname */
1208 if (!mapname
|| !domainname
|| *table_mapping
== NULL
)
1211 if (strchr(mapname
, COMMA_CHAR
))
1214 if ((map
= s_strndup(mapname
, strlen(mapname
))) == 0)
1217 if (getfullmapname(&map
, domainname
)) {
1222 *found_map
= find_table_mapping(map
, strlen(map
), *table_mapping
);
1233 * FUNCTION: append_domainContext
1235 * Higher level function to append the domains to the appropriate
1236 * fields in a table mapping structure. Calls either getfullmapname()
1237 * or make_full_dn() to do the actual append.
1239 * RETURNS: 0 on success, -1 on any error.
1243 append_domainContext(__nis_table_mapping_t
**table_map
,
1244 char *DomainLabel
, char *Domain
)
1246 __nis_table_mapping_t
*tmp_map
= *table_map
;
1248 char *tmp_dbId
= NULL
;
1250 int domain_specific
= 0;
1251 char *myself
= "append_domainContext";
1253 if (!DomainLabel
|| !Domain
|| !tmp_map
)
1255 if (tmp_map
->dbId
== NULL
|| tmp_map
->objName
== NULL
) {
1256 p_error
= parse_bad_map_error
;
1259 tmp_dbId
= s_strndup(tmp_map
->dbId
, strlen(tmp_map
->dbId
));
1262 if (strchr(tmp_map
->dbId
, COMMA_CHAR
)) {
1263 domain_specific
= 1;
1264 id
= (char *)strtok_r(tmp_dbId
, COMMA_STRING
, &lasts
);
1266 id
= (char *)strtok_r(NULL
, COMMA_STRING
, &lasts
);
1275 if (strcasecmp(id
, DomainLabel
)) {
1280 if (getfullmapname(&tmp_map
->dbId
, DomainLabel
)) {
1284 append_dot(&tmp_map
->dbId
);
1289 if (getfullmapname(&tmp_map
->objName
, DomainLabel
))
1291 append_dot(&tmp_map
->objName
);
1294 * If domain specific mapping doesn't have objectDN,
1295 * then don't touch. Most probably, pass for the generic mapping
1296 * will handle this by coping over it's own objectDN
1298 if (domain_specific
&& tmp_map
->objectDN
== NULL
)
1301 if (tmp_map
->objectDN
== NULL
) {
1302 /* Allocate memory to objectDN */
1303 tmp_map
->objectDN
= (__nis_object_dn_t
*)
1304 s_calloc(1, sizeof (__nis_object_dn_t
));
1305 if (tmp_map
->objectDN
== NULL
) {
1306 logmsg(MSG_NOMEM
, LOG_ERR
,
1307 "%s: Cannot allocate memory for objectDN",
1311 tmp_map
->objectDN
->read
.base
= NULL
;
1312 tmp_map
->objectDN
->write
.base
= NULL
;
1313 tmp_map
->objectDN
->read
.attrs
= NULL
;
1314 tmp_map
->objectDN
->write
.attrs
= NULL
;
1315 tmp_map
->objectDN
->read
.scope
= LDAP_SCOPE_ONELEVEL
;
1316 tmp_map
->objectDN
->write
.scope
= LDAP_SCOPE_UNKNOWN
;
1319 if (!make_fqdn(tmp_map
->objectDN
, Domain
))
1321 if (tmp_map
->objectDN
->write
.base
) {
1322 if (!make_full_dn(&tmp_map
->objectDN
->write
.base
, Domain
))