184 ret = cmd_edit_user(args); |
184 ret = cmd_edit_user(args); |
185 } else if(!strcasecmp(cmd, "version") || !strcasecmp(cmd, "-version") |
185 } else if(!strcasecmp(cmd, "version") || !strcasecmp(cmd, "-version") |
186 || !strcasecmp(cmd, "--version")) { |
186 || !strcasecmp(cmd, "--version")) { |
187 fprintf(stderr, "dav %s\n", DAV_VERSION); |
187 fprintf(stderr, "dav %s\n", DAV_VERSION); |
188 } else if(!strcasecmp(cmd, "complete")) { |
188 } else if(!strcasecmp(cmd, "complete")) { |
189 if(args->argc < 2) { |
189 ret = cmd_complete(args); |
190 return 1; |
|
191 } |
|
192 char *index_str = args->argv[0]; |
|
193 int64_t index = 0; |
|
194 if(!util_strtoint(index_str, &index)) { |
|
195 return 1; |
|
196 } |
|
197 if(args->argc + 2 != argc) { |
|
198 // we have to fix the index |
|
199 |
|
200 for(int i=2;i<args->argc;i++) { |
|
201 if(index == i-2) { |
|
202 break; |
|
203 } |
|
204 if(strcmp(argv[i+2], args->argv[i])) { |
|
205 index--; |
|
206 } |
|
207 } |
|
208 } |
|
209 |
|
210 ret = shell_completion(args, index); |
|
211 } else { |
190 } else { |
212 print_usage(argv[0]); |
191 print_usage(argv[0]); |
213 } |
192 } |
214 } |
193 } |
215 |
194 |
3000 int cmd_edit_user(CmdArgs *args) { |
2979 int cmd_edit_user(CmdArgs *args) { |
3001 return secretstore_cmd(args, FALSE, NULL, cmd_ss_edit_user, NULL); |
2980 return secretstore_cmd(args, FALSE, NULL, cmd_ss_edit_user, NULL); |
3002 } |
2981 } |
3003 |
2982 |
3004 |
2983 |
3005 int shell_completion(CmdArgs *args, int index) { |
2984 static char** read_args_from_stdin(int *argc) { |
3006 if(args->argc < 2 || args->argc < 3) { |
2985 // read stdin into buffer |
|
2986 UcxBuffer *in = ucx_buffer_new(NULL, 1024, UCX_BUFFER_AUTOEXTEND); |
|
2987 ucx_stream_copy(stdin, in, (read_func)fread, (write_func)ucx_buffer_write); |
|
2988 |
|
2989 // split input into lines |
|
2990 ssize_t count = 0; |
|
2991 sstr_t *lines = scstrsplit(scstrn(in->space, in->pos), SC("\n"), &count); |
|
2992 |
|
2993 char **args = NULL; |
|
2994 if(count > 0) { |
|
2995 args = calloc(count, sizeof(char*)); |
|
2996 for(int i=0;i<count;i++) { |
|
2997 args[i] = lines[i].ptr; |
|
2998 } |
|
2999 free(lines); |
|
3000 |
|
3001 *argc = count; |
|
3002 } else { |
|
3003 *argc = 0; |
|
3004 } |
|
3005 |
|
3006 // cleanup |
|
3007 ucx_buffer_free(in); |
|
3008 |
|
3009 return args; |
|
3010 } |
|
3011 |
|
3012 int cmd_complete(CmdArgs *args) { |
|
3013 if(args->argc != 1) { |
3007 return 1; |
3014 return 1; |
3008 } |
3015 } |
3009 |
3016 char *index_str = args->argv[0]; |
|
3017 int64_t index = 0; |
|
3018 if(!util_strtoint(index_str, &index)) { |
|
3019 return 1; |
|
3020 } |
|
3021 |
|
3022 // The completion bash script passes the input words to stdin |
|
3023 int comp_argc; |
|
3024 char **comp_argv = read_args_from_stdin(&comp_argc); |
|
3025 |
|
3026 // Try to parse the args |
|
3027 char *cmd = NULL; |
|
3028 if(comp_argc > 1) { |
|
3029 cmd = comp_argv[1]; |
|
3030 } |
|
3031 CmdArgs *comp_args = cmd_parse_args(comp_argc - 2, comp_argv + 2); |
|
3032 if(comp_args) { |
|
3033 // check whether the arglist contains options |
|
3034 if(comp_args->argc + 2 != comp_argc) { |
|
3035 // index points to the arg in the raw arglist, however we have to |
|
3036 // know the index for this item in comp_args->argv |
|
3037 // any arg that is an option or an option value creates a |
|
3038 // difference between the two lists |
|
3039 |
|
3040 // adjust index to comp_args->argv |
|
3041 int j = 0; |
|
3042 for(int i=0;i<comp_argc-2;i++) { |
|
3043 if(index == i-2) { |
|
3044 break; |
|
3045 } |
|
3046 |
|
3047 if(strcmp(comp_argv[i+2], comp_args->argv[j])) { |
|
3048 index--; |
|
3049 } else { |
|
3050 j++; |
|
3051 } |
|
3052 } |
|
3053 } |
|
3054 } else { |
|
3055 comp_args = NULL; |
|
3056 } |
|
3057 |
|
3058 // generate output for shell completion |
|
3059 int ret = 1; |
|
3060 if(comp_args) { |
|
3061 ret = shell_completion(cmd, comp_args, index); |
|
3062 } |
|
3063 |
|
3064 // cleanup |
|
3065 cmd_args_free(comp_args); |
|
3066 free(comp_argv); |
|
3067 return ret; |
|
3068 |
|
3069 } |
|
3070 |
|
3071 int shell_completion(char *cmd, CmdArgs *args, int index) { |
3010 if(index == 1) { |
3072 if(index == 1) { |
3011 sstr_t prefix = { NULL, 0 }; |
3073 sstr_t prefix = { NULL, 0 }; |
3012 if(args->argc > 2) { |
3074 if(cmd) { |
3013 prefix = sstr(args->argv[2]); |
3075 prefix = sstr(cmd); |
3014 } |
3076 } |
3015 for(int i=0;;i++) { |
3077 for(int i=0;;i++) { |
3016 char *str = cmdusageinfo[i]; |
3078 char *str = cmdusageinfo[i]; |
3017 if(!str) { |
3079 if(!str) { |
3018 break; |
3080 break; |
3033 printf("%.*s\n", (int)maxlen, str); |
3095 printf("%.*s\n", (int)maxlen, str); |
3034 } |
3096 } |
3035 return 0; |
3097 return 0; |
3036 } |
3098 } |
3037 |
3099 |
3038 char *cmd = args->argv[2]; |
|
3039 if(!strcmp(cmd, "date")) { |
3100 if(!strcmp(cmd, "date")) { |
3040 return 0; |
3101 return 0; |
3041 } |
3102 } |
3042 |
3103 |
3043 // get already typed URL or NULL, if the user hasn't started typing yet |
3104 // get already typed URL or NULL, if the user hasn't started typing yet |
3044 char *url = args->argc > 3 ? args->argv[3] : NULL; |
3105 char *url = args->argc > 0 ? args->argv[0] : NULL; |
3045 |
3106 |
3046 //printf("index: {%s}\n", args->argv[0]); |
3107 //printf("index: {%s}\n", args->argv[0]); |
3047 //printf("dav: {%s}\n", args->argv[1]); |
3108 //printf("dav: {%s}\n", args->argv[1]); |
3048 //printf("cmd: {%s}\n", cmd); |
3109 //printf("cmd: {%s}\n", cmd); |
3049 //printf("url: {%s}\n", url); |
3110 //printf("url: {%s}\n", url); |
3050 |
3111 |
3051 if(index == 2) { |
3112 if(index == 2) { |
3052 // url completion |
3113 // url completion |
3053 return url_completion(url); |
3114 return url_completion(args, url); |
3054 } else if (index == 3) { |
3115 } else if (index == 3) { |
3055 if(!strcmp(cmd, "put") || !strcmp(cmd, "import")) { |
3116 if(!strcmp(cmd, "put") || !strcmp(cmd, "import")) { |
3056 // file completion |
3117 // file completion |
3057 return 12; |
3118 return 12; |
3058 } else if(!strcmp(cmd, "copy") || !strcmp(cmd, "cp") || !strcmp(cmd, "move") || !strcmp(cmd, "mv")) { |
3119 } else if(!strcmp(cmd, "copy") || !strcmp(cmd, "cp") || !strcmp(cmd, "move") || !strcmp(cmd, "mv")) { |
3059 // url completion |
3120 // url completion |
3060 return url_completion(url); |
3121 return url_completion(args, url); |
3061 } |
3122 } |
3062 } |
3123 } |
3063 |
3124 |
3064 return 0; |
3125 return 0; |
3065 } |
3126 } |
3066 |
3127 |
3067 int url_completion(char *u) { |
3128 int url_completion(CmdArgs *args, char *u) { |
3068 sstr_t url; |
3129 sstr_t url; |
3069 url.ptr = u; |
3130 url.ptr = u; |
3070 url.length = u ? strlen(u) : 0; |
3131 url.length = u ? strlen(u) : 0; |
3071 |
3132 |
3072 // if the user wants the URL to be quoted, we conform to their wish |
3133 // if the user wants the URL to be quoted, we conform to their wish |
3106 } |
3167 } |
3107 |
3168 |
3108 } |
3169 } |
3109 } else { |
3170 } else { |
3110 // url completion |
3171 // url completion |
3111 |
3172 ucx_map_cstr_put(args->options, "noinput", ""); |
3112 CmdArgs a; |
|
3113 memset(&a, 0, sizeof(CmdArgs)); |
|
3114 a.options = ucx_map_new(4); |
|
3115 ucx_map_cstr_put(a.options, "noinput", ""); |
|
3116 |
3173 |
3117 char *path = NULL; |
3174 char *path = NULL; |
3118 Repository *repo = url2repo_s(url, &path); |
3175 Repository *repo = url2repo_s(url, &path); |
3119 DavSession *sn = connect_to_repo(repo, path, &a); |
3176 DavSession *sn = connect_to_repo(repo, path, args); |
3120 ucx_map_free(a.options); |
|
3121 if(!sn) { |
3177 if(!sn) { |
|
3178 return 0; |
|
3179 } |
|
3180 if(set_session_config(sn, args)) { |
3122 return 0; |
3181 return 0; |
3123 } |
3182 } |
3124 |
3183 |
3125 size_t plen = strlen(path); |
3184 size_t plen = strlen(path); |
3126 |
3185 |