r20: Add the registry library. Still needs a lot of work,
[ira/wip.git] / source4 / lib / registry / reg_backend_dir / reg_backend_dir.c
1 /* 
2    Unix SMB/CIFS implementation.
3    Registry interface
4    Copyright (C) Jelmer Vernooij                                          2004.
5    
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 2 of the License, or
9    (at your option) any later version.
10    
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.
15    
16    You should have received a copy of the GNU General Public License
17    along with this program; if not, write to the Free Software
18    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19 */
20
21 #include "includes.h"
22 #include "lib/registry/common/registry.h"
23
24 static DIR *reg_dir_dir(REG_HANDLE *h, const char *base, const char *name)
25 {
26         char *path = NULL;
27         DIR *d;
28         asprintf(&path, "%s/%s/%s", h->location, base, name);
29         path = reg_path_win2unix(path);
30         
31         d = opendir(path);
32         if(!d) {
33                 printf("Unable to open '%s'\n", path);
34                 return NULL;
35         }
36         SAFE_FREE(path);
37         return d;
38 }
39
40 static BOOL reg_dir_add_key(REG_KEY *parent, const char *name)
41 {
42         char *path;
43         int ret;
44         asprintf(&path, "%s/%s/%s", parent->handle->location, reg_key_get_path(parent), name);
45         path = reg_path_win2unix(path);
46         ret = mkdir(path, 0700);
47         free(path);
48         return (ret == 0);
49 }
50
51 static BOOL reg_dir_del_key(REG_KEY *k)
52 {
53         char *path;
54         int ret;
55         asprintf(&path, "%s/%s", k->handle->location, reg_key_get_path(k));
56         path = reg_path_win2unix(path);
57         ret = rmdir(path);
58         free(path);
59         return (ret == 0);
60 }
61
62 static REG_KEY *reg_dir_open_key(REG_HANDLE *h, const char *name)
63 {
64         DIR *d;
65         char *fullpath;
66         if(!name) {
67                 DEBUG(0, ("NULL pointer passed as directory name!"));
68                 return NULL;
69         }
70         fullpath = reg_path_win2unix(strdup(name));
71         d = reg_dir_dir(h, "", fullpath);
72         free(fullpath);
73         
74         if(d) return reg_key_new_abs(name, h, d);
75         return NULL;
76 }
77
78 static BOOL reg_dir_fetch_subkeys(REG_KEY *k, int *count, REG_KEY ***r)
79 {
80         DIR *d = (DIR *)k->backend_data;
81         struct dirent *e;
82         int max = 200;
83         REG_KEY **ar;
84         if(!d) return False;
85         rewinddir(d);
86         (*count) = 0;
87         ar = malloc(sizeof(REG_KEY *) * max);
88         
89         while((e = readdir(d))) {
90                 if(e->d_type == DT_DIR && 
91                    strcmp(e->d_name, ".") &&
92                    strcmp(e->d_name, "..")) {
93                         char *fullpath = reg_path_win2unix(strdup(k->path));
94                         ar[(*count)] = reg_key_new_rel(e->d_name, k, reg_dir_dir(k->handle, fullpath, e->d_name));
95                         free(fullpath);
96                         if(ar[(*count)])(*count)++;
97
98                         if((*count) == max) {
99                                 max+=200;
100                                 ar = realloc(ar, sizeof(REG_KEY *) * max);
101                         }
102                 }
103         }
104         
105         *r = ar;
106         return True;
107 }
108
109 static BOOL reg_dir_open(REG_HANDLE *h, const char *loc, BOOL try) {
110         if(!loc) return False;
111         return True;
112 }
113
114 static void dir_free(REG_KEY *k) 
115 {
116         closedir((DIR *)k->backend_data);
117 }
118
119 static REG_VAL *reg_dir_add_value(REG_KEY *p, const char *name, int type, void *data, int len)
120 {
121         REG_VAL *ret = reg_val_new(p, NULL);
122         char *fullpath;
123         FILE *fd;
124         ret->name = name?strdup(name):NULL;
125         fullpath = reg_path_win2unix(strdup(reg_val_get_path(ret)));
126         
127         fd = fopen(fullpath, "w+");
128         
129         /* FIXME */
130         return NULL;
131 }
132
133 static BOOL reg_dir_del_value(REG_VAL *v)
134 {
135         char *fullpath = reg_path_win2unix(strdup(reg_val_get_path(v)));
136         return False;
137 }
138
139 static REG_OPS reg_backend_dir = {
140         .name = "dir",
141         .open_registry = reg_dir_open,
142         .open_key = reg_dir_open_key,
143         .fetch_subkeys = reg_dir_fetch_subkeys,
144         .add_key = reg_dir_add_key,
145         .del_key = reg_dir_del_key,
146         .add_value = reg_dir_add_value,
147         .del_value = reg_dir_del_value,
148         .free_key_backend_data = dir_free
149 };
150
151 NTSTATUS reg_dir_init(void)
152 {
153         return register_backend("registry", &reg_backend_dir);
154 }