2016-04-10 13 views
-3

Das Ziel dieses Servers ist es, kleine Dateien auf relativ einfache Weise zu übertragen. Ich habe den Code abgeschlossen und alles kompiliert ohne Fehler, und wenn ich versuche, es auszuführen, hat die Serverseite keine Probleme, aber die Client-Seite gibt einen Fehler in der Socket-Bindung und einen Segmentierungsfehler. Ich habe mich gefragt, was im Code diese Probleme verursacht hat.Socket connect Fehler in C

Server:

#include <stdio.h> 
#include <sys/socket.h> 
#include <sys/stat.h> 
#include <sys/fcntl.h> 
#include <string.h> 
#include <unistd.h> 
#include <crypt.h> 
#include <time.h> 
#include <stdlib.h> 
#include <sys/types.h> 
#include <dirent.h> 
#include <netinet/ip.h> 
void timestamp_ss() 
{ 
    time_t current_time; 
    char* log_time; 

    log_time = ctime(&current_time); 
    log_file_ss(log_time); 
} 
send_data(int sockfd, char info_to_send) 
{ 
    char eof_buffer[4] = "\EOF"; 
    int sent_data, data_to_send; 
    data_to_send = strlen(&info_to_send); 

    while(data_to_send > 0) 
    { 
    sent_data = send(sockfd, &info_to_send, data_to_send, 0); 
    if(sent_data == -1) 
    perror("There was a problem in the sending of data!"); 
    data_to_send -= sent_data; 
    info_to_send += sent_data; 
    } 
    send(sockfd, eof_buffer, 4, 0); 
} 
int recv_data(int sockfd, char *dest_buffer) 
{ 
    #define EoF "\EOF" 
    unsigned char *buffer; 
    int eof_match = 0, eof_size = 2; 

    buffer = dest_buffer; 
    while(recv(sockfd, buffer, 1, 0) == 1) 
    { 
    if(*buffer == EoF[eof_match]) 
    { 
     eof_match++; 
     if(eof_match = eof_size) 
     { 
      *(buffer+1-eof_size) = '\0'; 
      return strlen(dest_buffer); 
     } 
     else 
     { 
      eof_match = 0; 
     } 
    } 
    buffer++; 
    } 
    return 0; 
} 
int password_ss(char *password_attempt, char *password_actual) 
{ 
    char key[] = { "ZjQXStSi" }; 
    char ivec[] = {"7eNP3U1b" }; 
    char des_dec[] = { "DES_DECRYPT" }; 
    char des_hw[] = { "DES_HW" }; 
    int l, i; 

    l = strlen(password_attempt); 
    i = cbc_crypt(key, password_attempt, l, *des_dec | *des_hw, ivec); 
    if(i < 0) 
    error_escape("In decryption"); 

    if(password_attempt == password_actual) 
    return 1; 
    else 
    return 0; 
} 
int log_file_ss(char *log_message) 
{ 
    char logfile[]= "/Server/log/C-File-Transfer-Server-Log"; 
    int log_fd, len; 

    log_fd = open(logfile, O_WRONLY | O_APPEND | O_CREAT); 
    len = strlen(log_message); 
    write(log_fd, log_message, len); 
} 
void file_to_client_ss(int sockfd, struct sockaddr_in *client_addr_ptr) 
{ 
    char file_req_c[128]; 
    char buffer[10000]; 
    char files[256]; 
    char pass_attempt[128]; 
    char *error_403[20] = { "Error 403: Forbidden" }; 
    char *error_404[25] = { "Error 404: File Not Found" }; 
    char *pass_path[20] = { "/server/log/PASSWORD" }; 
    char *pass_req[50] = { "This File Requires A Password, Please Enter It Now" }; 
    char *no_pass[37] = { "This File Does Not Require A Password" }; 
    char *username; 
    char *file_s; 
    char *string; 
    char *file1_path[26] = { "/server/received_files/r_w" }; 
    char *file2_path[24] = { "/server/received_files/r" }; 
    char *file3_path[24] = { "/server/received_files/n" }; 
    char file_data; 
    FILE *cs, *ps; 
    int file1, file2, file3, file_test, pass; 

    cs = fopen(file_req_c, "r"); 
    recv_data(sockfd, username); 
    chdir("/server/log/PASSWORD"); 
    ps = fopen(username, "r"); 
    fread(files, 1, file_size(ps), ps); 
    chdir("/server"); 
    recv_data(sockfd, file_req_c); 
    file_test = file_exist(file1_path, file_req_c); 
    if(file_test = -1) 
    { 
    file_test = file_exist(file2_path, file_req_c); 
    if(file_test = -1) 
    { 
     file_test = file_exist(file3_path, file_req_c); 
      if(file_test = -1) 
      { 
       error_escape("Opening file request from client"); 
      } 
      else 
      { 
        send_data(sockfd, **pass_req); 
        recv_data(sockfd, pass_attempt); 
        pass = password_ss(pass_attempt, files); 
         if(pass == 0) 
       { 
          send_data(sockfd, **error_403); 
          error_escape("Wrong Password"); 
       } 
        else 
        { 
          if(file_exist(pass_path, username) == 0) 
           send_data(sockfd, *file_req_c); 
        else 
         errror_escape("Error in sending file"); 
         } 
      } 
     } 
     else 
     { 
     chdir(*file2_path); 
     file_data = fread(buffer, 1, file_size(cs), cs); 
     send_data(sockfd, **no_pass); 
     send_data(sockfd, file_data); 
     }  
    } 
    else 
    { 
    chdir(*file1_path); 
    file_data = fread(buffer, 1, file_size(cs), cs); 
    send_data(sockfd, **no_pass); 
    send_data(sockfd, file_data); 
    } 
} 
int file_size(FILE *stream) 
{ 
    off_t file_len; 

    fseek(stream, 0, SEEK_END); 
    file_len = ftell(stream); 
    fclose(stream); 
    return file_len; 
} 
int file_exist(char *file_path, char *file_name) 
{ 
    DIR *dp; 
    FILE *fc; 
    struct dirent *ep; 

dp = opendir(file_path); 

    if(dp == NULL) 
    perror("Opening path"); 
    else 
    chdir(file_path); 
closedir(dp); 

fc = fopen(file_name, "r"); 
    if(fc == NULL) 
    { 
    perror("Opening file"); 
    return(-1); 
    } 
    else { 
    return(0); 
} 
} 
error_escape(char *problem) 
{ 
    char error_message[256]; 

    strcpy(error_message, "! There Has Been An Error !"); 
    strncat(error_message, problem, 173); 
    perror("Error: "); 
    log_file_ss(error_message); 
    timestamp_ss(); 
    exit(-1); 
} 
void file_accept_ss(int sockfd, struct sockaddr_in *client_addr_ptr) 
{ 
    char client_request[512], username[256], file_content[8192], buf[8192]; 
    char *client_r_w[26] = { "/server/received_files/r_w" }; 
    char *client_r[24] = { "/server/received_files/r" }; 
    char *client_n[24] = { "/server/received_files/n" }; 
    char *search_string_read[6] = { "O_READ" }; 
    char *search_string_w[14] = { "O_READANDWRITE" }; 
    char *password_path[20] = { "/server/log/PASSWORD" }; 
    char *mkdir[37] = { "/server/log/PASSWORD" }; 
    char *ret; 
    char file_data, recv_i; 
    char password[256]; 
    int change_dir_test, recv_check; 
    FILE *fn, *Ps; 

    recv_data(sockfd, username); 
    recv_data(sockfd, password); 
    strcat(*mkdir, username); 
    strcat(*mkdir, password); 
    fn = fopen(*mkdir, "a"); 
    chdir(*password_path); 
    Ps = fopen(*mkdir, "a"); 
    chdir("/server"); 
    recv_i = fread(buf, 1, file_size(fn), fn); 
    recv_check = recv_data(sockfd, &recv_i); 
    if(recv_check = -1) 
    error_escape("! There Was An Error In The Receiving Of The File From The Client !"); 
    fread(file_content, 8, file_size(fn), fn); 
    ret = strstr(file_content, *search_string_read); 
    if(ret = NULL) 
    { 
    change_dir_test = chdir(*client_n); 
     if(change_dir_test = -1) 
     error_escape("! There Was An Error In The Changing Of Directories !"); 
     else 
     { 
    file_data = fread(buf, 1, file_size(Ps), Ps); 
     recv_data(sockfd, &file_data); 
     chdir(*client_n); 
    strcat(*client_n, username); 
     rename(username, *client_n); 
     } 
    } 
    if(ret = *search_string_read) 
    { 
    change_dir_test = chdir(*client_r); 
     if(change_dir_test = -1) 
     error_escape("! There Was An Error In The Changing Of Directories !"); 
     else 
     { 
     chdir(*client_r); 
     rename(username, *client_r); 
     } 
    } 
    if(ret = *search_string_w) 
    { 
    change_dir_test = chdir(*client_r_w); 
     if(change_dir_test = -1) 
     error_escape("! There Was An Error In The Changing Of Directories !"); 
     else 
     { 
     chdir(*client_r_w); 
     rename(username, *client_r_w); 
    } 
    } 
    log_file_ss("Client:"); 
    log_file_ss(username); 
    timestamp_ss(); 
} 
int main(void) 
{ 
    struct sockaddr_in server, client; 
    int sockfd, bind_test, listen_test, client_sockfd, sin_size; 

    sockfd = socket(PF_INET, SOCK_STREAM, 0); 
    if(sockfd == -1) 
    error_escape("Making Socket"); 

    server.sin_family = AF_INET; 
    server.sin_port = htons(80); 
    server.sin_addr.s_addr = INADDR_ANY; 

    bind_test = bind(sockfd, (struct sockaddr *)&server, sizeof(server)); 
    if(bind_test < 0) 
    error_escape("Binding Socket"); 
    listen_test = listen(sockfd, 20); 
    if(listen_test < 0) 
    error_escape("Listening"); 
    while(1) 
    { 
    sin_size = sizeof(struct sockaddr_in); 
    client_sockfd = accept(sockfd, (struct sockaddr *)&client, &sin_size); 
    file_accept_ss(client_sockfd, &client); 
    file_to_client_ss(client_sockfd, &client); 
    } 
shutdown(client_sockfd, SHUT_RDWR); 
return 0; 
} 

Auftraggeber:

#include <stdio.h> 
#include <string.h> 
#include <dirent.h> 
#include <sys/types.h> 
#include <unistd.h> 
#include <crypt.h> 
#include <sys/socket.h> 
#include <netinet/ip.h> 



send_data(int sockfd, char info_to_send) 
{ 
    char eof_buffer[4] = "\EOF"; 
    int sent_data, data_to_send; 
    data_to_send = strlen(&info_to_send); 

    while(data_to_send > 0) 
    { 
    sent_data = send(sockfd, &info_to_send, data_to_send, 0); 
    if(sent_data == -1) 
    perror("There was a problem in the sending of data!"); 
    data_to_send -= sent_data; 
    info_to_send += sent_data; 
    } 
    send(sockfd, eof_buffer, 4, 0); 
} 
send_file_cs(int sockfd) 
{ 
    char file_buffer[4096], file_name[256]; 
    char name, username, password; 
    char *search_st, file_data, *file_location; 
    int perm_choice, password_max = 20, ch; 
    off_t size_of_file; 
    FILE *fp; 

    printf("%s\n", "Please enter the path to file you would like to move to server:"); 
    scanf("%s", &file_location); 
    ch = chdir(file_location); 
    if(ch == -1) 
    perror("! There Has Been An Error In The Directory Path !"); 
    else 
    chdir(file_location); 
    printf("%s\n", "Now Enter The Name Of The File You Would Like To Transfer:"); 
    printf("%s\n", "! Warning, The File May Not Exceed 4 kilobytes !"); 
    scanf("%s", &name); 
    printf("%s", "What would you like the username for this file to be?"); 
    name = *file_name; 
    size_of_file = file_size(fp); 
    if(size_of_file > 4096) 
    printf("! The File Is Greater Than 4 Kilobytes !"); 
    fp = fopen(file_name, "r+"); 
    printf("%s\n", "What Permissions Would You Like The File To Have?\n (1) For Other Clients To See The File\n (2) For Other CLients To See But Not Be Able To Access\n (3) Other Clients Cannot See Or Access The File"); 
    scanf("%d", &perm_choice); 
    if(perm_choice > 3 || perm_choice < 1) 
    perror("! Incorrect Permissions !"); 
    if(perm_choice = 1) 
    { 
    search_st = "O_READ"; 
    fopen(file_name, "a"); 
    fwrite(search_st, 1, strlen(search_st), fp); 
    } 
    if(perm_choice = 2) 
    { 
    search_st = "O_READANDWRITE"; 
    fopen(file_name, "a"); 
    fwrite(search_st, 1, strlen(search_st), fp); 
    } 
    if(perm_choice = 3) 
    { 
    search_st = "O_NOACCESS"; 
    fopen(file_name, "a"); 
    fwrite(search_st, 1, strlen(search_st), fp); 
    printf("%s", "Please enter a password"); 
    scanf("%s", &password); 
    send_data(sockfd, password); 
    } 
    file_data = fread(file_buffer, 1, 4096, fp); 
    send_data(sockfd, file_data); 
}  
int recv_data(int sockfd, char *dest_buffer) 
{ 
    #define EoF "\EOF" 
    unsigned char *buffer; 
    int eof_match = 0, eof_size = 2; 

    buffer = dest_buffer; 
    while(recv(sockfd, buffer, 1, 0) == 1) 
    { 
    if(*buffer == EoF[eof_match]) 
    { 
     eof_match++; 
     if(eof_match = eof_size) 
     { 
      *(buffer+1-eof_size) = '\0'; 
      return strlen(dest_buffer); 
     } 
     else 
     { 
      eof_match = 0; 
     } 
    } 
    buffer++; 
    } 
    return 0; 
} 
int password_cs(int max_length, int sockfd) 
{ 
    char salt[] = { "ZjQXStSi" }; 
    char ivec[] = { "7eNP3U1b" }; 
    char des_enc[] = { "DES_ENCRYPT" }; 
    char des_hw[] = { "DES_HW" }; 
    char password; 
    char *ret, *ret2; 
    int l, i; 

    printf("%s", "Please set your password:"); 
    scanf("%s", &password); 
    l = strlen(&password); 
    if(l > max_length) 
    printf("%s : %d", "Password must be less than", max_length); 

    i = cbc_crypt(salt, password, l, *des_enc | *des_hw, ivec); 
    if(i < 0) 
    perror("In erncryption"); 

    send_data(sockfd, password); 
    return 0; 
} 
int file_size(FILE *stream) 
{ 
    off_t file_len; 

    fseek(stream, 0, SEEK_END); 
    file_len = ftell(stream); 
    fclose(stream); 
    return file_len; 
} 
int file_exist(char *file_path, char *file_name) 
{ 
    DIR *dp; 
    FILE *fc; 
    struct dirent *ep; 

dp = opendir(file_path); 

    if(dp == NULL) 
    perror("Opening path"); 
    else 
    chdir(file_path); 
closedir(dp); 

fc = fopen(file_name, "r"); 
    if(fc == NULL) 
    { 
    perror("Opening file"); 
    return(-1); 
    } 
    else { 
    return(0); 
} 
} 
void client_request_file_cs(int sockfd) 
{ 
    char password_buf[128], file[4096], recv_file[256]; 
    char *requires[16] = { "Requires" }; 
    char *str, *restr, *file_contents, *name2, *path, *rebuf; 
    char file_req, password, name, username; 
    int test; 
    FILE *re; 

    printf("%s\n", "What file would you like from the server?"); 
    scanf("%s", &file_req); 
    printf("%s", "What is the user name associated with the file?"); 
    scanf("%s", &username); 
    send_data(sockfd, username); 
    printf("%s\n", "Where Would You Like The File To Be Put, Please Enter The Path:"); 
    scanf("%s", &path); 
    test = chdir(path); 
    if(test == -1) 
    printf("%s\n", "Invalid Path"); 
    printf("%s\n", "What Would You Like To Call The File?"); 
    scanf("%s", &name); 
    name2 = &name; 
    re = fopen(name2, "w"); 
    fread(file_contents, 1, file_size(re), re); 
    send_data(sockfd, file_req); 
    recv_data(sockfd, password_buf); 
    printf("%s\n", password_buf); 
    str = strstr(password_buf, *requires); 
    if(str == NULL) 
    recv_data(sockfd, file); 
    else 
    { 
    scanf("%s", &password); 
    send_data(sockfd, password); 
    } 
    recv_data(sockfd, rebuf); 
    fwrite(rebuf, 1, sizeof(rebuf), re); 
    fclose(re); 
    restr = strstr(file_contents, "error_"); 
    if(restr != NULL) 
    printf("%s\n", re); 
} 
int main(void) 
{ 
struct sockaddr_in client, server_addr; 
int sockfd, connected; 

server_addr.sin_family = AF_INET; 
server_addr.sin_port = htons(80); 

sockfd = socket(AF_INET, SOCK_STREAM, 0); 
if(sockfd == -1) 
    printf("%s", "Error opening socket"); 

connected = connect(sockfd, (struct sockaddr *)&server_addr, sizeof(struct sockaddr)); 
if(connected == -1) 
    printf("%s", "Error binding socket"); 

send_file_cs(sockfd); 
client_request_file_cs(sockfd); 
shutdown(sockfd, SHUT_RDWR); 
return 0; 
} 

Danke im Voraus für jede Hilfe.

+2

Haben Sie diesen Code mit einem Debugger durchgegangen? – abelenky

+1

Ich kann nicht finden, wie Sie 'server_addr.sin_addr.s_addr' in Ihrem Klientencode einstellen. Es scheint, dass Sie 'connect' mit der Adresse aufrufen, die nicht initialisiert ist, was schlecht ist, aber möglicherweise nicht das einzige Problem ist. –

+0

Es scheint, als ob das Verbindungsproblem den Fehler "Connection Refused" gibt –

Antwort

0

Unter anderen gültigen Fragen/Punkten in den Kommentaren, Speicherzuweisung in Ihrem Code zu Ihren Segmentierungsfehlern beitragen kann ...

char *file_location (und andere) werden als verwendet werden, wenn der Speicher zugewiesen wurde.

Ihre Verwendung der Variablen in scanf("%s", &file_location); vor dem Zuweisen von Speicher ruft undefiniertes Verhalten auf und ist wahrscheinlich (zumindest teilweise) für Ihre Laufzeitfehler verantwortlich.

Speicher hinzufügen vor die Scanf-Anweisung. Hier sind zwei Beispiele dafür, wie das zu tun:

1) Erstellen Sie Heap-Speicher (mit [m] [c] alloc):

char *file_location;  

file_location = malloc(MAX_FILENAME_LEN);//or your systems value for max directory length 
if(file_location) 
{ 
    scanf("%s", &file_location); 
    ... 

2) Verwenden Sie Stapelspeicher: (zeigen Sie Ihre Zeiger auf einen Ort mit Speicher)

char file_name[256]; 
char *file_location = file_name; 

file_location = file_name; 
scanf("%s", &file_location); 

Aber der einfachste Weg (wenn es nichts beschränke Sie einen Zeiger verwenden) wäre, nur die Variable auf dem Stapel zu erstellen und verwenden Sie es in scanf(...):

char file_location[256]; 

scanf("%s", &file_location); 

Es gibt andere Variablen (neben file_location) in Ihrem Beispielcode, die vor der Verwendung Speicher benötigen. Denken Sie daran, alle Variablen mit dem erstellten Speicher on the heap freizugeben, wenn Sie fertig sind.

+0

Nach dem Ausprobieren dieser beiden, gibt es immer noch Fehler "Bad Address" egal welche Adresse ich eingegeben. –

+0

@WinnerInc - Ich bot die Speichererstellung Problem/Lösung als nur eine von mehreren möglichen Probleme mit Ihrem Code Beispiel, die müssen angesprochen werden, bevor Sie es zum Laufen bringen. Hast du 'server_addr.sin_addr.s_addr' irgendwo initialisiert? Haben Sie es selbst mit einem Debugger versucht? (Ich würde, außer ich bin zu diesem Zeitpunkt nicht in der Nähe meines Compilers) – ryyker

0

binden Fehler

Es gibt keine Bind Fehler hier. Der Client macht überhaupt keine Bindung. Es wird ein Fehler Verbindung der Socket, und dann irreführend druckt "Bind Fehler".

Der Verbindungsfehler besteht darin, dass Sie das Adressfeld des Ziels, mit dem Sie eine Verbindung herstellen möchten, nicht initialisieren.

NB Sie brauchen \ EOF nicht. recv() gibt Null zurück, wenn der Peer die Verbindung trennt, für die Sie nicht suchen. Sie überprüfen es auch nicht auf Fehler. Das ist ein sehr seltsamer Code. - EJP vor 19 Minuten