1 | #include <sys/types.h>
|
---|
2 | #include <unistd.h>
|
---|
3 | #include <dirent.h>
|
---|
4 | #include <errno.h>
|
---|
5 | #include <stdio.h>
|
---|
6 | #include <string.h>
|
---|
7 | #include <popt.h>
|
---|
8 | #include <stdlib.h>
|
---|
9 | #include <libsmbclient.h>
|
---|
10 | #include "get_auth_data_fn.h"
|
---|
11 |
|
---|
12 | static void browse(char * path,
|
---|
13 | int scan,
|
---|
14 | int indent);
|
---|
15 |
|
---|
16 |
|
---|
17 | static void
|
---|
18 | get_auth_data_with_context_fn(SMBCCTX * context,
|
---|
19 | const char * pServer,
|
---|
20 | const char * pShare,
|
---|
21 | char * pWorkgroup,
|
---|
22 | int maxLenWorkgroup,
|
---|
23 | char * pUsername,
|
---|
24 | int maxLenUsername,
|
---|
25 | char * pPassword,
|
---|
26 | int maxLenPassword);
|
---|
27 |
|
---|
28 | int main(int argc, const char *argv[])
|
---|
29 | {
|
---|
30 | int debug = 0;
|
---|
31 | int debug_stderr = 0;
|
---|
32 | int no_auth = 0;
|
---|
33 | int context_auth = 0;
|
---|
34 | int scan = 0;
|
---|
35 | int iterations = -1;
|
---|
36 | int opt;
|
---|
37 | char * p;
|
---|
38 | char buf[1024];
|
---|
39 | poptContext pc;
|
---|
40 | SMBCCTX * context;
|
---|
41 | struct poptOption long_options[] =
|
---|
42 | {
|
---|
43 | POPT_AUTOHELP
|
---|
44 | {
|
---|
45 | "debug", 'd', POPT_ARG_INT, &debug,
|
---|
46 | 0, "Set debug level", "integer"
|
---|
47 | },
|
---|
48 | {
|
---|
49 | "stderr", 'e', POPT_ARG_NONE, &debug_stderr,
|
---|
50 | 0, "Debug log to stderr instead of stdout", "integer"
|
---|
51 | },
|
---|
52 | {
|
---|
53 | "scan", 's', POPT_ARG_NONE, &scan,
|
---|
54 | 0, "Scan for servers and shares", "integer"
|
---|
55 | },
|
---|
56 | {
|
---|
57 | "iterations", 'i', POPT_ARG_INT, &iterations,
|
---|
58 | 0, "Iterations", "integer"
|
---|
59 | },
|
---|
60 | {
|
---|
61 | "noauth", 'A', POPT_ARG_NONE, &no_auth,
|
---|
62 | 0, "Do not request authentication data", "integer"
|
---|
63 | },
|
---|
64 | {
|
---|
65 | "contextauth", 'C', POPT_ARG_NONE, &context_auth,
|
---|
66 | 0, "Use new authentication function with context", "integer"
|
---|
67 | },
|
---|
68 | {
|
---|
69 | NULL
|
---|
70 | }
|
---|
71 | };
|
---|
72 |
|
---|
73 | setbuf(stdout, NULL);
|
---|
74 |
|
---|
75 | pc = poptGetContext("opendir", argc, argv, long_options, 0);
|
---|
76 |
|
---|
77 | poptSetOtherOptionHelp(pc, "");
|
---|
78 |
|
---|
79 | while ((opt = poptGetNextOpt(pc)) != -1) {
|
---|
80 | printf("Got option %d = %c\n", opt, opt);
|
---|
81 | switch (opt) {
|
---|
82 | }
|
---|
83 | }
|
---|
84 |
|
---|
85 | /* Allocate a new context */
|
---|
86 | context = smbc_new_context();
|
---|
87 | if (!context) {
|
---|
88 | printf("Could not allocate new smbc context\n");
|
---|
89 | return 1;
|
---|
90 | }
|
---|
91 |
|
---|
92 | /* If we're scanning, do no requests for authentication data */
|
---|
93 | if (scan) {
|
---|
94 | no_auth = 1;
|
---|
95 | }
|
---|
96 |
|
---|
97 | /* Set mandatory options (is that a contradiction in terms?) */
|
---|
98 | smbc_setDebug(context, debug);
|
---|
99 | if (context_auth) {
|
---|
100 | smbc_setFunctionAuthDataWithContext(context,
|
---|
101 | get_auth_data_with_context_fn);
|
---|
102 | smbc_setOptionUserData(context, strdup("hello world"));
|
---|
103 | } else {
|
---|
104 | smbc_setFunctionAuthData(context, get_auth_data_fn);
|
---|
105 | }
|
---|
106 |
|
---|
107 | smbc_setOptionUseKerberos(context, 1);
|
---|
108 | smbc_setOptionFallbackAfterKerberos(context, 1);
|
---|
109 |
|
---|
110 | /* If we've been asked to log to stderr instead of stdout, ... */
|
---|
111 | if (debug_stderr) {
|
---|
112 | /* ... then set the option to do so */
|
---|
113 | smbc_setOptionDebugToStderr(context, 1);
|
---|
114 | }
|
---|
115 |
|
---|
116 | /* Initialize the context using the previously specified options */
|
---|
117 | if (!smbc_init_context(context)) {
|
---|
118 | smbc_free_context(context, 0);
|
---|
119 | printf("Could not initialize smbc context\n");
|
---|
120 | return 1;
|
---|
121 | }
|
---|
122 |
|
---|
123 | /* Tell the compatibility layer to use this context */
|
---|
124 | smbc_set_context(context);
|
---|
125 |
|
---|
126 | if (scan)
|
---|
127 | {
|
---|
128 | for (; iterations != 0;) {
|
---|
129 | if (iterations > 0) {
|
---|
130 | iterations--;
|
---|
131 | }
|
---|
132 |
|
---|
133 | snprintf(buf, sizeof(buf), "smb://");
|
---|
134 | browse(buf, scan, 0);
|
---|
135 | }
|
---|
136 | }
|
---|
137 | else
|
---|
138 | {
|
---|
139 | for (; iterations != 0;) {
|
---|
140 | if (iterations > 0) {
|
---|
141 | iterations--;
|
---|
142 | }
|
---|
143 |
|
---|
144 | fputs("url: ", stdout);
|
---|
145 | p = fgets(buf, sizeof(buf), stdin);
|
---|
146 | if (! p)
|
---|
147 | {
|
---|
148 | break;
|
---|
149 | }
|
---|
150 |
|
---|
151 | if ((p = strchr(buf, '\n')) != NULL)
|
---|
152 | {
|
---|
153 | *p = '\0';
|
---|
154 | }
|
---|
155 |
|
---|
156 | browse(buf, scan, 0);
|
---|
157 | }
|
---|
158 | }
|
---|
159 |
|
---|
160 | exit(0);
|
---|
161 | }
|
---|
162 |
|
---|
163 | static void
|
---|
164 | get_auth_data_with_context_fn(SMBCCTX * context,
|
---|
165 | const char * pServer,
|
---|
166 | const char * pShare,
|
---|
167 | char * pWorkgroup,
|
---|
168 | int maxLenWorkgroup,
|
---|
169 | char * pUsername,
|
---|
170 | int maxLenUsername,
|
---|
171 | char * pPassword,
|
---|
172 | int maxLenPassword)
|
---|
173 | {
|
---|
174 | printf("Authenticating with context %p", context);
|
---|
175 | if (context != NULL) {
|
---|
176 | char *user_data = smbc_getOptionUserData(context);
|
---|
177 | printf(" with user data %s", user_data);
|
---|
178 | }
|
---|
179 | printf("\n");
|
---|
180 |
|
---|
181 | get_auth_data_fn(pServer, pShare, pWorkgroup, maxLenWorkgroup,
|
---|
182 | pUsername, maxLenUsername, pPassword, maxLenPassword);
|
---|
183 | }
|
---|
184 |
|
---|
185 | static void browse(char * path, int scan, int indent)
|
---|
186 | {
|
---|
187 | char * p;
|
---|
188 | char buf[1024];
|
---|
189 | int dir;
|
---|
190 | struct stat st;
|
---|
191 | struct smbc_dirent * dirent;
|
---|
192 |
|
---|
193 | if (! scan)
|
---|
194 | {
|
---|
195 | printf("Opening (%s)...\n", path);
|
---|
196 | }
|
---|
197 |
|
---|
198 | if ((dir = smbc_opendir(path)) < 0)
|
---|
199 | {
|
---|
200 | printf("Could not open directory [%s] (%d:%s)\n",
|
---|
201 | path, errno, strerror(errno));
|
---|
202 | return;
|
---|
203 | }
|
---|
204 |
|
---|
205 | while ((dirent = smbc_readdir(dir)) != NULL)
|
---|
206 | {
|
---|
207 | printf("%*.*s%-30s", indent, indent, "", dirent->name);
|
---|
208 |
|
---|
209 | switch(dirent->smbc_type)
|
---|
210 | {
|
---|
211 | case SMBC_WORKGROUP:
|
---|
212 | printf("WORKGROUP");
|
---|
213 | break;
|
---|
214 |
|
---|
215 | case SMBC_SERVER:
|
---|
216 | printf("SERVER");
|
---|
217 | break;
|
---|
218 |
|
---|
219 | case SMBC_FILE_SHARE:
|
---|
220 | printf("FILE_SHARE");
|
---|
221 | break;
|
---|
222 |
|
---|
223 | case SMBC_PRINTER_SHARE:
|
---|
224 | printf("PRINTER_SHARE");
|
---|
225 | break;
|
---|
226 |
|
---|
227 | case SMBC_COMMS_SHARE:
|
---|
228 | printf("COMMS_SHARE");
|
---|
229 | break;
|
---|
230 |
|
---|
231 | case SMBC_IPC_SHARE:
|
---|
232 | printf("IPC_SHARE");
|
---|
233 | break;
|
---|
234 |
|
---|
235 | case SMBC_DIR:
|
---|
236 | printf("DIR");
|
---|
237 | break;
|
---|
238 |
|
---|
239 | case SMBC_FILE:
|
---|
240 | printf("FILE");
|
---|
241 |
|
---|
242 | p = path + strlen(path);
|
---|
243 | strcat(p, "/");
|
---|
244 | strcat(p+1, dirent->name);
|
---|
245 | if (smbc_stat(path, &st) < 0)
|
---|
246 | {
|
---|
247 | printf(" unknown size (reason %d: %s)",
|
---|
248 | errno, strerror(errno));
|
---|
249 | }
|
---|
250 | else
|
---|
251 | {
|
---|
252 | printf(" size %lu", (unsigned long) st.st_size);
|
---|
253 | }
|
---|
254 | *p = '\0';
|
---|
255 |
|
---|
256 | break;
|
---|
257 |
|
---|
258 | case SMBC_LINK:
|
---|
259 | printf("LINK");
|
---|
260 | break;
|
---|
261 | }
|
---|
262 |
|
---|
263 | printf("\n");
|
---|
264 |
|
---|
265 | if (scan &&
|
---|
266 | (dirent->smbc_type == SMBC_WORKGROUP ||
|
---|
267 | dirent->smbc_type == SMBC_SERVER))
|
---|
268 | {
|
---|
269 | /*
|
---|
270 | * don't append server name to workgroup; what we want is:
|
---|
271 | *
|
---|
272 | * smb://workgroup_name
|
---|
273 | * or
|
---|
274 | * smb://server_name
|
---|
275 | *
|
---|
276 | */
|
---|
277 | snprintf(buf, sizeof(buf), "smb://%s", dirent->name);
|
---|
278 | browse(buf, scan, indent + 2);
|
---|
279 | }
|
---|
280 | }
|
---|
281 |
|
---|
282 | smbc_closedir(dir);
|
---|
283 | }
|
---|
284 |
|
---|