2 * Unix SMB/CIFS implementation.
3 * Virtual Windows Registry Layer
4 * Copyright (C) Gerald Carter 2002-2005
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 3 of the License, or
9 * (at your option) any later version.
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, see <http://www.gnu.org/licenses/>.
20 /* Implementation of registry frontend view functions. */
25 #define DBGC_CLASS DBGC_REGISTRY
27 /**********************************************************************
29 Note that the struct regsubkey_ctr and REGVAL_CTR objects *must* be
30 talloc()'d since the methods use the object pointer as the talloc
31 context for internal private data.
33 There is no longer a regval_ctr_intit() and regval_ctr_destroy()
34 pair of functions. Simply TALLOC_ZERO_P() and TALLOC_FREE() the
37 **********************************************************************/
39 WERROR
regsubkey_ctr_init(TALLOC_CTX
*mem_ctx
, struct regsubkey_ctr
**ctr
)
42 return WERR_INVALID_PARAM
;
45 *ctr
= talloc_zero(mem_ctx
, struct regsubkey_ctr
);
53 WERROR
regsubkey_ctr_set_seqnum(struct regsubkey_ctr
*ctr
, int seqnum
)
56 return WERR_INVALID_PARAM
;
64 int regsubkey_ctr_get_seqnum(struct regsubkey_ctr
*ctr
)
73 /***********************************************************************
74 Add a new key to the array
75 **********************************************************************/
77 WERROR
regsubkey_ctr_addkey( struct regsubkey_ctr
*ctr
, const char *keyname
)
85 /* make sure the keyname is not already there */
87 if ( regsubkey_ctr_key_exists( ctr
, keyname
) ) {
91 if (!(newkeys
= TALLOC_REALLOC_ARRAY(ctr
, ctr
->subkeys
, char *,
92 ctr
->num_subkeys
+1))) {
96 ctr
->subkeys
= newkeys
;
98 if (!(ctr
->subkeys
[ctr
->num_subkeys
] = talloc_strdup(ctr
->subkeys
,
101 * Don't shrink the new array again, this wastes a pointer
110 /***********************************************************************
111 Delete a key from the array
112 **********************************************************************/
114 int regsubkey_ctr_delkey( struct regsubkey_ctr
*ctr
, const char *keyname
)
119 return ctr
->num_subkeys
;
121 /* make sure the keyname is actually already there */
123 for ( i
=0; i
<ctr
->num_subkeys
; i
++ ) {
124 if ( strequal( ctr
->subkeys
[i
], keyname
) )
128 if ( i
== ctr
->num_subkeys
)
129 return ctr
->num_subkeys
;
131 /* update if we have any keys left */
133 if ( i
< ctr
->num_subkeys
)
134 memmove(&ctr
->subkeys
[i
], &ctr
->subkeys
[i
+1],
135 sizeof(char*) * (ctr
->num_subkeys
-i
));
137 return ctr
->num_subkeys
;
140 /***********************************************************************
141 Check for the existance of a key
142 **********************************************************************/
144 bool regsubkey_ctr_key_exists( struct regsubkey_ctr
*ctr
, const char *keyname
)
152 for ( i
=0; i
<ctr
->num_subkeys
; i
++ ) {
153 if ( strequal( ctr
->subkeys
[i
],keyname
) )
160 /***********************************************************************
161 How many keys does the container hold ?
162 **********************************************************************/
164 int regsubkey_ctr_numkeys( struct regsubkey_ctr
*ctr
)
166 return ctr
->num_subkeys
;
169 /***********************************************************************
170 Retreive a specific key string
171 **********************************************************************/
173 char* regsubkey_ctr_specific_key( struct regsubkey_ctr
*ctr
, uint32 key_index
)
175 if ( ! (key_index
< ctr
->num_subkeys
) )
178 return ctr
->subkeys
[key_index
];
182 * Utility functions for REGVAL_CTR
185 /***********************************************************************
186 How many keys does the container hold ?
187 **********************************************************************/
189 int regval_ctr_numvals( REGVAL_CTR
*ctr
)
191 return ctr
->num_values
;
194 /***********************************************************************
195 allocate memory for and duplicate a REGISTRY_VALUE.
196 This is malloc'd memory so the caller should free it when done
197 **********************************************************************/
199 REGISTRY_VALUE
* dup_registry_value( REGISTRY_VALUE
*val
)
201 REGISTRY_VALUE
*copy
= NULL
;
206 if ( !(copy
= SMB_MALLOC_P( REGISTRY_VALUE
)) ) {
207 DEBUG(0,("dup_registry_value: malloc() failed!\n"));
211 /* copy all the non-pointer initial data */
213 memcpy( copy
, val
, sizeof(REGISTRY_VALUE
) );
218 if ( val
->data_p
&& val
->size
)
220 if ( !(copy
->data_p
= (uint8
*)memdup( val
->data_p
,
222 DEBUG(0,("dup_registry_value: memdup() failed for [%d] "
223 "bytes!\n", val
->size
));
227 copy
->size
= val
->size
;
233 /**********************************************************************
234 free the memory allocated to a REGISTRY_VALUE
235 *********************************************************************/
237 void free_registry_value( REGISTRY_VALUE
*val
)
242 SAFE_FREE( val
->data_p
);
248 /**********************************************************************
249 *********************************************************************/
251 uint8
* regval_data_p( REGISTRY_VALUE
*val
)
256 /**********************************************************************
257 *********************************************************************/
259 uint32
regval_size( REGISTRY_VALUE
*val
)
264 /**********************************************************************
265 *********************************************************************/
267 char* regval_name( REGISTRY_VALUE
*val
)
269 return val
->valuename
;
272 /**********************************************************************
273 *********************************************************************/
275 uint32
regval_type( REGISTRY_VALUE
*val
)
280 /***********************************************************************
281 Retreive a pointer to a specific value. Caller shoud dup the structure
282 since this memory will go away when the ctr is free()'d
283 **********************************************************************/
285 REGISTRY_VALUE
* regval_ctr_specific_value( REGVAL_CTR
*ctr
, uint32 idx
)
287 if ( !(idx
< ctr
->num_values
) )
290 return ctr
->values
[idx
];
293 /***********************************************************************
294 Check for the existance of a value
295 **********************************************************************/
297 bool regval_ctr_key_exists( REGVAL_CTR
*ctr
, const char *value
)
301 for ( i
=0; i
<ctr
->num_values
; i
++ ) {
302 if ( strequal( ctr
->values
[i
]->valuename
, value
) )
309 /***********************************************************************
310 * compose a REGISTRY_VALUE from input data
311 **********************************************************************/
313 REGISTRY_VALUE
*regval_compose(TALLOC_CTX
*ctx
, const char *name
, uint16 type
,
314 const char *data_p
, size_t size
)
316 REGISTRY_VALUE
*regval
= TALLOC_P(ctx
, REGISTRY_VALUE
);
318 if (regval
== NULL
) {
322 fstrcpy(regval
->valuename
, name
);
325 regval
->data_p
= (uint8
*)TALLOC_MEMDUP(regval
, data_p
, size
);
326 if (!regval
->data_p
) {
331 regval
->data_p
= NULL
;
338 /***********************************************************************
339 Add a new registry value to the array
340 **********************************************************************/
342 int regval_ctr_addvalue( REGVAL_CTR
*ctr
, const char *name
, uint16 type
,
343 const char *data_p
, size_t size
)
346 return ctr
->num_values
;
348 /* Delete the current value (if it exists) and add the new one */
350 regval_ctr_delvalue( ctr
, name
);
352 /* allocate a slot in the array of pointers */
354 if ( ctr
->num_values
== 0 ) {
355 ctr
->values
= TALLOC_P( ctr
, REGISTRY_VALUE
*);
357 ctr
->values
= TALLOC_REALLOC_ARRAY(ctr
, ctr
->values
,
367 /* allocate a new value and store the pointer in the arrya */
369 ctr
->values
[ctr
->num_values
] = regval_compose(ctr
, name
, type
, data_p
,
371 if (ctr
->values
[ctr
->num_values
] == NULL
) {
377 return ctr
->num_values
;
380 /***********************************************************************
381 Add a new registry value to the array
382 **********************************************************************/
384 int regval_ctr_copyvalue( REGVAL_CTR
*ctr
, REGISTRY_VALUE
*val
)
387 regval_ctr_addvalue(ctr
, val
->valuename
, val
->type
,
388 (char *)val
->data_p
, val
->size
);
391 return ctr
->num_values
;
394 /***********************************************************************
395 Delete a single value from the registry container.
396 No need to free memory since it is talloc'd.
397 **********************************************************************/
399 int regval_ctr_delvalue( REGVAL_CTR
*ctr
, const char *name
)
403 for ( i
=0; i
<ctr
->num_values
; i
++ ) {
404 if ( strequal( ctr
->values
[i
]->valuename
, name
) )
408 /* just return if we don't find it */
410 if ( i
== ctr
->num_values
)
411 return ctr
->num_values
;
413 /* If 'i' was not the last element, just shift everything down one */
415 if ( i
< ctr
->num_values
)
416 memmove(&ctr
->values
[i
], &ctr
->values
[i
+1],
417 sizeof(REGISTRY_VALUE
*)*(ctr
->num_values
-i
));
419 return ctr
->num_values
;
422 /***********************************************************************
423 Retrieve single value from the registry container.
424 No need to free memory since it is talloc'd.
425 **********************************************************************/
427 REGISTRY_VALUE
* regval_ctr_getvalue( REGVAL_CTR
*ctr
, const char *name
)
431 /* search for the value */
433 for ( i
=0; i
<ctr
->num_values
; i
++ ) {
434 if ( strequal( ctr
->values
[i
]->valuename
, name
) )
435 return ctr
->values
[i
];
441 /***********************************************************************
442 return the data_p as a uint32
443 **********************************************************************/
445 uint32
regval_dword( REGISTRY_VALUE
*val
)
449 data
= IVAL( regval_data_p(val
), 0 );
454 /***********************************************************************
455 return the data_p as a character string
456 **********************************************************************/
458 char *regval_sz(REGISTRY_VALUE
*val
)
462 rpcstr_pull_talloc(talloc_tos(), &data
,
463 regval_data_p(val
), regval_size(val
),0);