Ejemplo n.º 1
0
/* FIXME: The error code returned here is never checked. */
static int sec_set_protection_level(struct connectdata *conn)
{
  int code;
  char *pbsz;
  static unsigned int buffer_size = 1 << 20; /* 1048576 */
  enum protection_level level = conn->request_data_prot;

  DEBUGASSERT(level > PROT_NONE && level < PROT_LAST);

  if(!conn->sec_complete) {
    infof(conn->data, "Trying to change the protection level after the"
                      "completion of the data exchange.\n");
    return -1;
  }

  /* Bail out if we try to set up the same level */
  if(conn->data_prot == level)
    return 0;

  if(level) {
    code = ftp_send_command(conn, "PBSZ %u", buffer_size);
    if(code < 0)
      return -1;

    if(code/100 != 2) {
      failf(conn->data, "Failed to set the protection's buffer size.");
      return -1;
    }
    conn->buffer_size = buffer_size;

    pbsz = strstr(conn->data->state.buffer, "PBSZ=");
    if(pbsz) {
      /* ignore return code, use default value if it fails */
      (void)sscanf(pbsz, "PBSZ=%u", &buffer_size);
      if(buffer_size < conn->buffer_size)
        conn->buffer_size = buffer_size;
    }
  }

  /* Now try to negiociate the protection level. */
  code = ftp_send_command(conn, "PROT %c", level_to_char(level));

  if(code < 0)
    return -1;

  if(code/100 != 2) {
    failf(conn->data, "Failed to set the protection level.");
    return -1;
  }

  conn->data_prot = level;
  if(level == PROT_PRIVATE)
    conn->command_prot = level;

  return 0;
}
Ejemplo n.º 2
0
int ftp_disconnect(ftp_t* ftp) {
    char answer[MAX_STRING_SIZE];
    if(ftp_read_answer(ftp, answer, MAX_STRING_SIZE) < 0) {
        printf("Error in disconnecing from server\n");
        return -1;
    }

    if(ftp_send_command(ftp, "quit\n", strlen("quit\n")) < 0) {
        printf("Error in sending quit command\n");
        return -1;
    }

    if(close(ftp->socketfd) < 0) {
        printf("Failed to close ftp socket.\n");
        return -1;
    }

    if(close(ftp->datafd) < 0) {
        printf("Failed to close ftp data socket.\n");
        return -1;
    }

    printf("Disconnected from server.\n");
    return 0;
}
Ejemplo n.º 3
0
int ftp_login_host(ftp_t* ftp) {

    char command[6 + strlen(ftp->username)];
    char answer[MAX_STRING_SIZE];

    sprintf(command,"user %s\n", ftp->username);
    if(ftp_send_command(ftp, command, strlen(command)) < 0) {
        printf("Error while sending login information\n");
        return -1;
    }
    if(ftp_read_answer(ftp, answer, MAX_STRING_SIZE) < 0) {
        printf("Error while receiving answer from login information \n");
        return -1;
    }

    sprintf(command,"pass %s\n", ftp->password);

    if(ftp_send_command(ftp, command, strlen(command)) < 0) {
        printf("Error while sending login information\n");
        return -1;
    }

    if(ftp_read_answer(ftp, answer, MAX_STRING_SIZE) < 0) {
        printf("Error while receiving answer from login information \n");
        return -1;
    }

    int replyCode;
    sscanf(answer, "%d", &replyCode);
    if(replyCode == LOGIN_FAIL) { /* Failed to login */
        printf("Wrong username/password combination.\n");
        return -1;
    }

    printf("Logged in to server %s.\n",ftp->server_address);

    return 0;
}
Ejemplo n.º 4
0
int ftp_retr_file(ftp_t* ftp) {
    char command[6+strlen(ftp->path_to_file)];
    char answer[MAX_STRING_SIZE];
    sprintf(command, "retr %s\n", ftp->path_to_file);

    printf("Requesting file %s\n",basename(ftp->path_to_file));

    if(ftp_send_command(ftp, command, 6+strlen(ftp->path_to_file)) < 0) {
        printf("Error in requesting file from server\n");
        return -1;
    }
    if(ftp_read_answer(ftp, answer, MAX_STRING_SIZE) < 0) {
        printf("Error in reading answer from file request from server\n");
        return -1;
    }

    int replyCode;
    sscanf(answer, "%d", &replyCode);
    if(replyCode == OPEN_FILE_FAIL) { /* Failed to find file */
        printf("Couldn't find file %s in server.\n", ftp->path_to_file);
        return -1;
    }
    else if(replyCode == OPEN_FILE_SUCCESS) {
        /* Find the file size to export it */
        char* beg = strrchr(answer,'(');
        char sizeInfo[MAX_STRING_SIZE];
        strcpy(sizeInfo, beg);
        int size;
        sscanf(sizeInfo, "(%d bytes).", &size);
        ftp->file_size = size;
#ifdef DEBUG
        printf("DEBUG : Size Info: %d bytes\n", size);
#endif
    }

#ifdef DEBUG
    printf("%s\n", answer);
#endif

    return 0;
}
Ejemplo n.º 5
0
int ftp_set_passive_mode(ftp_t* ftp) {
    char answer[MAX_STRING_SIZE];
    int ip1, ip2, ip3, ip4;
    int port1, port2;
    if(ftp_send_command(ftp, "pasv\n", strlen("pasv\n")) < 0) {
        printf("Error while switching to passive mode\n");
        return -1;
    }
    if(ftp_read_answer(ftp, answer, MAX_STRING_SIZE) < 0) {
        printf("Error while receiving answer from switching to passive mode \n");
        return -1;
    }

#ifdef DEBUG
    printf("%s", answer);
#endif

    if ((sscanf(answer, "227 Entering Passive Mode (%d,%d,%d,%d,%d,%d)", &ip1, &ip2, &ip3, &ip4, &port1, &port2)) < 0) {
        printf("Error while parsing pasv answer from the server.\n");
        return -1;
    }

    char ip[15];
    int port = 256*port1+port2;
    sprintf(ip, "%d.%d.%d.%d", ip1, ip2, ip3, ip4);

#ifdef DEBUG
    printf("IP: %s Port: %d\n", ip, port);
#endif

    int datafd = ftp_connect_socket(ip, port);
    if(datafd < 0) {
        printf("Error while connecting to data socket\n");
        return -1;
    }

    ftp->datafd = datafd;
    return 0;
}
Ejemplo n.º 6
0
static CURLcode choose_mech(struct connectdata *conn)
{
  int ret;
  struct Curl_easy *data = conn->data;
  void *tmp_allocation;
  const struct Curl_sec_client_mech *mech = &Curl_krb5_client_mech;

  tmp_allocation = realloc(conn->app_data, mech->size);
  if(tmp_allocation == NULL) {
    failf(data, "Failed realloc of size %u", mech->size);
    mech = NULL;
    return CURLE_OUT_OF_MEMORY;
  }
  conn->app_data = tmp_allocation;

  if(mech->init) {
    ret = mech->init(conn->app_data);
    if(ret) {
      infof(data, "Failed initialization for %s. Skipping it.\n",
            mech->name);
      return CURLE_FAILED_INIT;
    }
  }

  infof(data, "Trying mechanism %s...\n", mech->name);
  ret = ftp_send_command(conn, "AUTH %s", mech->name);
  if(ret < 0)
    /* FIXME: This error is too generic but it is OK for now. */
    return CURLE_COULDNT_CONNECT;

  if(ret/100 != 3) {
    switch(ret) {
    case 504:
      infof(data, "Mechanism %s is not supported by the server (server "
            "returned ftp code: 504).\n", mech->name);
      break;
    case 534:
      infof(data, "Mechanism %s was rejected by the server (server returned "
            "ftp code: 534).\n", mech->name);
      break;
    default:
      if(ret/100 == 5) {
        infof(data, "server does not support the security extensions\n");
        return CURLE_USE_SSL_FAILED;
      }
      break;
    }
    return CURLE_LOGIN_DENIED;
  }

  /* Authenticate */
  ret = mech->auth(conn->app_data, conn);

  if(ret != AUTH_CONTINUE) {
    if(ret != AUTH_OK) {
      /* Mechanism has dumped the error to stderr, don't error here. */
      return -1;
    }
    DEBUGASSERT(ret == AUTH_OK);

    conn->mech = mech;
    conn->sec_complete = 1;
    conn->recv[FIRSTSOCKET] = sec_recv;
    conn->send[FIRSTSOCKET] = sec_send;
    conn->recv[SECONDARYSOCKET] = sec_recv;
    conn->send[SECONDARYSOCKET] = sec_send;
    conn->command_prot = PROT_SAFE;
    /* Set the requested protection level */
    /* BLOCKING */
    (void)sec_set_protection_level(conn);
  }

  return CURLE_OK;
}