Annotation of embedaddon/curl/lib/curl_path.c, revision 1.1
1.1 ! misho 1: /***************************************************************************
! 2: * _ _ ____ _
! 3: * Project ___| | | | _ \| |
! 4: * / __| | | | |_) | |
! 5: * | (__| |_| | _ <| |___
! 6: * \___|\___/|_| \_\_____|
! 7: *
! 8: * Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
! 9: *
! 10: * This software is licensed as described in the file COPYING, which
! 11: * you should have received as part of this distribution. The terms
! 12: * are also available at https://curl.haxx.se/docs/copyright.html.
! 13: *
! 14: * You may opt to use, copy, modify, merge, publish, distribute and/or sell
! 15: * copies of the Software, and permit persons to whom the Software is
! 16: * furnished to do so, under the terms of the COPYING file.
! 17: *
! 18: * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
! 19: * KIND, either express or implied.
! 20: *
! 21: ***************************************************************************/
! 22:
! 23: #include "curl_setup.h"
! 24:
! 25: #if defined(USE_SSH)
! 26:
! 27: #include <curl/curl.h>
! 28: #include "curl_memory.h"
! 29: #include "curl_path.h"
! 30: #include "escape.h"
! 31: #include "memdebug.h"
! 32:
! 33: /* figure out the path to work with in this particular request */
! 34: CURLcode Curl_getworkingpath(struct connectdata *conn,
! 35: char *homedir, /* when SFTP is used */
! 36: char **path) /* returns the allocated
! 37: real path to work with */
! 38: {
! 39: struct Curl_easy *data = conn->data;
! 40: char *real_path = NULL;
! 41: char *working_path;
! 42: size_t working_path_len;
! 43: CURLcode result =
! 44: Curl_urldecode(data, data->state.up.path, 0, &working_path,
! 45: &working_path_len, FALSE);
! 46: if(result)
! 47: return result;
! 48:
! 49: /* Check for /~/, indicating relative to the user's home directory */
! 50: if(conn->handler->protocol & CURLPROTO_SCP) {
! 51: real_path = malloc(working_path_len + 1);
! 52: if(real_path == NULL) {
! 53: free(working_path);
! 54: return CURLE_OUT_OF_MEMORY;
! 55: }
! 56: if((working_path_len > 3) && (!memcmp(working_path, "/~/", 3)))
! 57: /* It is referenced to the home directory, so strip the leading '/~/' */
! 58: memcpy(real_path, working_path + 3, working_path_len - 2);
! 59: else
! 60: memcpy(real_path, working_path, 1 + working_path_len);
! 61: }
! 62: else if(conn->handler->protocol & CURLPROTO_SFTP) {
! 63: if((working_path_len > 1) && (working_path[1] == '~')) {
! 64: size_t homelen = strlen(homedir);
! 65: real_path = malloc(homelen + working_path_len + 1);
! 66: if(real_path == NULL) {
! 67: free(working_path);
! 68: return CURLE_OUT_OF_MEMORY;
! 69: }
! 70: /* It is referenced to the home directory, so strip the
! 71: leading '/' */
! 72: memcpy(real_path, homedir, homelen);
! 73: real_path[homelen] = '/';
! 74: real_path[homelen + 1] = '\0';
! 75: if(working_path_len > 3) {
! 76: memcpy(real_path + homelen + 1, working_path + 3,
! 77: 1 + working_path_len -3);
! 78: }
! 79: }
! 80: else {
! 81: real_path = malloc(working_path_len + 1);
! 82: if(real_path == NULL) {
! 83: free(working_path);
! 84: return CURLE_OUT_OF_MEMORY;
! 85: }
! 86: memcpy(real_path, working_path, 1 + working_path_len);
! 87: }
! 88: }
! 89:
! 90: free(working_path);
! 91:
! 92: /* store the pointer for the caller to receive */
! 93: *path = real_path;
! 94:
! 95: return CURLE_OK;
! 96: }
! 97:
! 98: /* The get_pathname() function is being borrowed from OpenSSH sftp.c
! 99: version 4.6p1. */
! 100: /*
! 101: * Copyright (c) 2001-2004 Damien Miller <djm@openbsd.org>
! 102: *
! 103: * Permission to use, copy, modify, and distribute this software for any
! 104: * purpose with or without fee is hereby granted, provided that the above
! 105: * copyright notice and this permission notice appear in all copies.
! 106: *
! 107: * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
! 108: * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
! 109: * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
! 110: * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
! 111: * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
! 112: * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
! 113: * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
! 114: */
! 115: CURLcode Curl_get_pathname(const char **cpp, char **path, char *homedir)
! 116: {
! 117: const char *cp = *cpp, *end;
! 118: char quot;
! 119: unsigned int i, j;
! 120: size_t fullPathLength, pathLength;
! 121: bool relativePath = false;
! 122: static const char WHITESPACE[] = " \t\r\n";
! 123:
! 124: if(!*cp) {
! 125: *cpp = NULL;
! 126: *path = NULL;
! 127: return CURLE_QUOTE_ERROR;
! 128: }
! 129: /* Ignore leading whitespace */
! 130: cp += strspn(cp, WHITESPACE);
! 131: /* Allocate enough space for home directory and filename + separator */
! 132: fullPathLength = strlen(cp) + strlen(homedir) + 2;
! 133: *path = malloc(fullPathLength);
! 134: if(*path == NULL)
! 135: return CURLE_OUT_OF_MEMORY;
! 136:
! 137: /* Check for quoted filenames */
! 138: if(*cp == '\"' || *cp == '\'') {
! 139: quot = *cp++;
! 140:
! 141: /* Search for terminating quote, unescape some chars */
! 142: for(i = j = 0; i <= strlen(cp); i++) {
! 143: if(cp[i] == quot) { /* Found quote */
! 144: i++;
! 145: (*path)[j] = '\0';
! 146: break;
! 147: }
! 148: if(cp[i] == '\0') { /* End of string */
! 149: /*error("Unterminated quote");*/
! 150: goto fail;
! 151: }
! 152: if(cp[i] == '\\') { /* Escaped characters */
! 153: i++;
! 154: if(cp[i] != '\'' && cp[i] != '\"' &&
! 155: cp[i] != '\\') {
! 156: /*error("Bad escaped character '\\%c'",
! 157: cp[i]);*/
! 158: goto fail;
! 159: }
! 160: }
! 161: (*path)[j++] = cp[i];
! 162: }
! 163:
! 164: if(j == 0) {
! 165: /*error("Empty quotes");*/
! 166: goto fail;
! 167: }
! 168: *cpp = cp + i + strspn(cp + i, WHITESPACE);
! 169: }
! 170: else {
! 171: /* Read to end of filename - either to white space or terminator */
! 172: end = strpbrk(cp, WHITESPACE);
! 173: if(end == NULL)
! 174: end = strchr(cp, '\0');
! 175: /* return pointer to second parameter if it exists */
! 176: *cpp = end + strspn(end, WHITESPACE);
! 177: pathLength = 0;
! 178: relativePath = (cp[0] == '/' && cp[1] == '~' && cp[2] == '/');
! 179: /* Handling for relative path - prepend home directory */
! 180: if(relativePath) {
! 181: strcpy(*path, homedir);
! 182: pathLength = strlen(homedir);
! 183: (*path)[pathLength++] = '/';
! 184: (*path)[pathLength] = '\0';
! 185: cp += 3;
! 186: }
! 187: /* Copy path name up until first "white space" */
! 188: memcpy(&(*path)[pathLength], cp, (int)(end - cp));
! 189: pathLength += (int)(end - cp);
! 190: (*path)[pathLength] = '\0';
! 191: }
! 192: return CURLE_OK;
! 193:
! 194: fail:
! 195: Curl_safefree(*path);
! 196: return CURLE_QUOTE_ERROR;
! 197: }
! 198:
! 199: #endif /* if SSH is used */
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>