1 #pragma ident	"%Z%%M%	%I%	%E% SMI"
2 
3 /*
4  * WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING
5  *
6  *	Openvision retains the copyright to derivative works of
7  *	this source code.  Do *NOT* create a derivative of this
8  *	source code before consulting with your legal department.
9  *	Do *NOT* integrate *ANY* of this source code into another
10  *	product before consulting with your legal department.
11  *
12  *	For further information, read the top-level Openvision
13  *	copyright which is contained in the top-level MIT Kerberos
14  *	copyright.
15  *
16  * WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING
17  *
18  */
19 
20 
21 #include    <unistd.h>
22 #include    <string.h>
23 #include    <stdlib.h>
24 #ifdef HAVE_MEMORY_H
25 #include    <memory.h>
26 #endif
27 
28 #include    <kadm5/adb.h>
29 #include    "import_err.h"
30 #include    "kdb5_util.h"
31 #include    "nstrtok.h"
32 
33 #define LINESIZE	32768 /* XXX */
34 #define PLURAL(count)	(((count) == 1) ? error_message(IMPORT_SINGLE_RECORD) : error_message(IMPORT_PLURAL_RECORDS))
35 
36 static int parse_pw_hist_ent(current, hist)
37    char *current;
38    osa_pw_hist_ent *hist;
39 {
40      int tmp, i, j, ret;
41      char *cp;
42 
43      ret = 0;
44      hist->n_key_data = 1;
45 
46      hist->key_data = (krb5_key_data *) malloc(hist->n_key_data *
47 					       sizeof(krb5_key_data));
48      if (hist->key_data == NULL)
49 	  return ENOMEM;
50      memset(hist->key_data, 0, sizeof(krb5_key_data)*hist->n_key_data);
51 
52      for (i = 0; i < hist->n_key_data; i++) {
53 	  krb5_key_data *key_data = &hist->key_data[i];
54 
55 	  key_data->key_data_ver = 1;
56 
57 	  if((cp = nstrtok((char *) NULL, "\t")) == NULL) {
58 	       com_err(NULL, IMPORT_BAD_RECORD, "%s", current);
59 	       ret = IMPORT_FAILED;
60 	       goto done;
61 	  }
62 	  key_data->key_data_type[0] = atoi(cp);
63 
64 	  if((cp = nstrtok((char *) NULL, "\t")) == NULL) {
65 	       com_err(NULL, IMPORT_BAD_RECORD, "%s", current);
66 	       ret =  IMPORT_FAILED;
67 	       goto done;
68 	  }
69 	  key_data->key_data_length[0] = atoi(cp);
70 
71 	  if((cp = nstrtok((char *) NULL, "\t")) == NULL) {
72 	       com_err(NULL, IMPORT_BAD_RECORD, "%s", current);
73 	       ret = IMPORT_FAILED;
74 	       goto done;
75 	  }
76 	  if(!(key_data->key_data_contents[0] =
77 	       (krb5_octet *) malloc(key_data->key_data_length[0]+1))) {
78 	       ret = ENOMEM;
79 	       goto done;
80 	  }
81 	  for(j = 0; j < key_data->key_data_length[0]; j++) {
82 	       if(sscanf(cp, "%02x", &tmp) != 1) {
83 		    com_err(NULL, IMPORT_BAD_RECORD, "%s", current);
84 		    ret = IMPORT_FAILED;
85 		    goto done;
86 	       }
87 	       key_data->key_data_contents[0][j] = tmp;
88 	       cp = strchr(cp, ' ') + 1;
89 	  }
90      }
91 
92 done:
93      return ret;
94 }
95 
96 /*
97  * Function: parse_principal
98  *
99  * Purpose: parse principal line in db dump file
100  *
101  * Arguments:
102  * 	<return value>	0 on success, error code on failure
103  *
104  * Requires:
105  *	principal database to be opened.
106  *	nstrtok(3) to have a valid buffer in memory.
107  *
108  * Effects:
109  *	[effects]
110  *
111  * Modifies:
112  *	[modifies]
113  *
114  */
115 int process_ov_principal(fname, kcontext, filep, verbose, linenop, pol_db)
116     char		*fname;
117     krb5_context	kcontext;
118     FILE		*filep;
119     int			verbose;
120     int			*linenop;
121     void *pol_db;
122 {
123     XDR			    xdrs;
124     osa_princ_ent_t	    rec;
125     osa_adb_ret_t	    ret;
126     krb5_tl_data	    tl_data;
127     krb5_principal	    princ;
128     krb5_db_entry	    kdb;
129     char		    *current;
130     char		    *cp;
131     int			    x, one;
132     krb5_boolean	    more;
133     char		    line[LINESIZE];
134 
135     if (fgets(line, LINESIZE, filep) == (char *) NULL) {
136 	 return IMPORT_BAD_FILE;
137     }
138     if((cp = nstrtok(line, "\t")) == NULL)
139 	return IMPORT_BAD_FILE;
140     if((rec = (osa_princ_ent_t) malloc(sizeof(osa_princ_ent_rec))) == NULL)
141 	return ENOMEM;
142     memset(rec, 0, sizeof(osa_princ_ent_rec));
143     if((ret = krb5_parse_name(kcontext, cp, &princ)))
144 	goto done;
145     krb5_unparse_name(kcontext, princ, &current);
146     if((cp = nstrtok((char *) NULL, "\t")) == NULL) {
147 	com_err(NULL, IMPORT_BAD_RECORD, "%s", current);
148 	ret =  IMPORT_FAILED;
149 	goto done;
150     } else {
151 	if(strcmp(cp, "")) {
152 	    if((rec->policy = (char *) malloc(strlen(cp)+1)) == NULL)  {
153 		ret = ENOMEM;
154 		goto done;
155 	    }
156 	    strcpy(rec->policy, cp);
157 	} else rec->policy = NULL;
158     }
159     if((cp = nstrtok((char *) NULL, "\t")) == NULL) {
160 	com_err(NULL, IMPORT_BAD_RECORD, "%s", current);
161 	ret = IMPORT_FAILED;
162 	goto done;
163     }
164     rec->aux_attributes = strtol(cp, (char  **)NULL, 16);
165     if((cp = nstrtok((char *) NULL, "\t")) == NULL) {
166 	com_err(NULL, IMPORT_BAD_RECORD, "%s", current);
167 	ret = IMPORT_FAILED;
168 	goto done;
169     }
170     rec->old_key_len = atoi(cp);
171     if((cp = nstrtok((char *) NULL, "\t")) == NULL) {
172 	com_err(NULL, IMPORT_BAD_RECORD, "%s", current);
173 	ret = IMPORT_FAILED;
174 	goto done;
175     }
176     rec->old_key_next = atoi(cp);
177     if((cp = nstrtok((char *) NULL, "\t")) == NULL) {
178 	com_err(NULL, IMPORT_BAD_RECORD, "%s", current);
179 	ret = IMPORT_FAILED;
180 	goto done;
181     }
182     rec->admin_history_kvno = atoi(cp);
183     if (! rec->old_key_len) {
184        rec->old_keys = NULL;
185     } else {
186        if(!(rec->old_keys = (osa_pw_hist_ent *)
187 	    malloc(sizeof(osa_pw_hist_ent) * rec->old_key_len))) {
188 	  ret = ENOMEM;
189 	  goto done;
190        }
191        memset(rec->old_keys,0,
192 	      sizeof(osa_pw_hist_ent) * rec->old_key_len);
193        for(x = 0; x < rec->old_key_len; x++)
194 	    parse_pw_hist_ent(current, &rec->old_keys[x]);
195     }
196 
197     xdralloc_create(&xdrs, XDR_ENCODE);
198     if (! xdr_osa_princ_ent_rec(&xdrs, rec)) {
199 	 xdr_destroy(&xdrs);
200 	 ret = OSA_ADB_XDR_FAILURE;
201 	 goto done;
202     }
203 
204     tl_data.tl_data_type = KRB5_TL_KADM_DATA;
205     tl_data.tl_data_length = xdr_getpos(&xdrs);
206     tl_data.tl_data_contents = (krb5_octet *) xdralloc_getdata(&xdrs);
207 
208     one = 1;
209     ret = krb5_db_get_principal(kcontext, princ, &kdb, &one, &more);
210     if (ret)
211 	 goto done;
212 
213     ret = krb5_dbe_update_tl_data(kcontext, &kdb, &tl_data);
214     if (ret)
215 	 goto done;
216 
217     ret = krb5_db_put_principal(kcontext, &kdb, &one);
218     if (ret)
219 	 goto done;
220 
221     xdr_destroy(&xdrs);
222 
223     (*linenop)++;
224 
225 done:
226     free(current);
227     krb5_free_principal(kcontext, princ);
228     osa_free_princ_ent(rec);
229     return ret;
230 }
231