2

こんにちは、これらが必要な TCP クライアント/サーバーを作成しようとしています。クライアントは、ファイルのファイル名またはファイル名のパスを提供します。サーバーはそのファイルを見つけて、権限、サイズ、所有者、所有者のグループ、変更/作成日、単語数、ユーザーの ID と優先度などの詳細を提供し、何か問題が発生した場合はこれらを -1 のクライアントに送信します。クライアントその詳細を印刷します。私はこのことをたくさんしましたが、大きな問題があるので続行できません.私の問題は、サーバーがファイルのパスを認識できないことですが、ファイルに名前を付けて通信しようとしました.違う?前もって感謝します

    CLIENT
        #include <stdio.h>
        #include <stdlib.h>
        #include <string.h>
        #include <sys/types.h>
        #include <sys/socket.h>
        #include <netinet/in.h>
        #include <netdb.h> 

        void error(char *msg)
        {
            perror(msg);
            exit(0);
        }

        int main(int argc, char *argv[])
        {
            int sockfd, portno, n;
            struct sockaddr_in serv_addr;
            struct hostent *server;

            char buffer[1024];
            if (argc < 3) {
               fprintf(stderr,"usage %s hostname port\n", argv[0]);
               exit(0);
            }
            portno = atoi(argv[2]);
            sockfd = socket(AF_INET, SOCK_STREAM, 0);
            if (sockfd < 0) 
                error("ERROR opening socket");
            server = gethostbyname(argv[1]);
            if (server == NULL) {
                fprintf(stderr,"ERROR, no such host\n");
                exit(0);
            }
            bzero((char *) &serv_addr, sizeof(serv_addr));
            serv_addr.sin_family = AF_INET;
            bcopy((char *)server->h_addr, 
                 (char *)&serv_addr.sin_addr.s_addr,
                 server->h_length);
            serv_addr.sin_port = htons(portno);
            if (connect(sockfd,&serv_addr,sizeof(serv_addr)) < 0) 
                error("ERROR connecting");
            printf("Please enter the filename or path of filename: ");
            bzero(buffer,1024);
            fgets(buffer,1024,stdin);
            n = write(sockfd,buffer,strlen(buffer));
            if (n < 0) 
                 error("ERROR writing to socket");
            bzero(buffer,1024);
            n = read(sockfd,buffer,1024);
            if (n < 0) 
                 error("ERROR reading from socket");
            printf("%s\n",buffer);
            return 0;



SERVER
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/types.h> 
#include <sys/socket.h>
#include <netinet/in.h>
#include <sys/resource.h>
#include <sys/time.h> 

void error(char *msg)
{
    perror(msg);
    exit(1);
}

int main(int argc, char *argv[])
{    
     FILE *fp;
     int sockfd, newsockfd, portno, clilen,i;
     char buffer[1024],filename[1024];
     char * pPath;
     struct sockaddr_in serv_addr, cli_addr;
     int n;
     int which = PRIO_PROCESS;
     id_t pid;
     int ret;
     if (argc < 2) {
         fprintf(stderr,"ERROR, no port provided\n");
         exit(1);
     }
     sockfd = socket(AF_INET, SOCK_STREAM, 0);
     if (sockfd < 0) 
        error("ERROR opening socket");
     bzero((char *) &serv_addr, sizeof(serv_addr));
     portno = atoi(argv[1]);
     serv_addr.sin_family = AF_INET;
     serv_addr.sin_addr.s_addr = INADDR_ANY;
     serv_addr.sin_port = htons(portno);
     if (bind(sockfd, (struct sockaddr *) &serv_addr,
              sizeof(serv_addr)) < 0) 
              error("ERROR on binding");
     listen(sockfd,5);
     clilen = sizeof(cli_addr);
     newsockfd = accept(sockfd, 
                 (struct sockaddr *) &cli_addr, 
                 &clilen);
     if (newsockfd < 0) 
          error("ERROR on accept");
     bzero(buffer,1024);
     n = read(newsockfd,buffer,1024);
     if (n < 0) error("ERROR reading from socket");
     printf("Here is the message: %s\n",buffer);

     system("ls -al 1.txt > ls.txt");
     system("wc -w 1.txt > wc.txt");



     /* pPath = getenv ("PATH");
     if (pPath!=NULL)
     printf ("The current path is: %s\n",pPath);

     system("touch path.txt");
     fp=fopen("path.txt","w");
      if (fp==NULL) exit(1);
 fprintf(fp,pPath);
     fclose(fp); */


     pid = getpid();
     ret = getpriority(which, pid);
     printf("priority %d user id %d ret %d",which,pid,ret);

system("paste ls.txt wc.txt user.txt > info.txt");

    fp=fopen("info.txt","r");

    if (fp==NULL) exit(1);

    for(int i=0;i<1000;i++){

            fscanf(fp,"%c",&buffer[i]);
    }
    fclose(fp);        

     n = write(newsockfd,buffer,1024);
     if (n < 0) error("ERROR writing to socket");
     return 0; 
}
    }`

迅速な返信ありがとうございます。具体的には、教授は私が作成したこのtxtファイルを作成するように依頼しませんでしたが、解決策を見つけることができず、すべてをバッファに書き込むことができなかったために作成しました。 :

バッファクライアントからのパスが付属していますバッファからパスファイルを見つけます(ここで問題があります)ls -alバッファに書き込みます(.txtに書きました)wcバッファに書き込みます(.txtに書きました)パス書き込み先バッファ (まだ行っていません) ユーザー情報 バッファに書き込みます (まだ行っていません) バッファ クライアントに送信 クライアントはこれらすべての情報を含むバッファを出力します

私は sprintf を試しましたが、あなたがそれをどのように使用するか正確には理解できませんでした.

4

5 に答える 5

0

サーバーに渡されたパスに末尾の '\n' が含まれていますか? その場合は、それを削除する必要があります (たとえば、\0 文字を配置することによって)

于 2010-11-22T09:14:36.223 に答える
0

このように返信して申し訳ありませんが、私はアカウントを持っていませんでした.私はこれに慣れていません.

char lsbuf[1024];
sprintf(lsbuf,"ls -al %s > ls.txt",buffer);
system(lsbuf);

ほとんど魅力のように機能しています...パスを受け入れてlsを実行しますが、lsをls.txtに保存せず(空のファイルを作成します)、バッファに送信しません。また、memsetを置き換えてみましたが、動作しています!!

于 2010-11-22T12:06:53.547 に答える
0

おそらく、パスをシステム コールに渡す必要があるでしょう。バッファーを割り当て (セキュリティのためにバッファーのチェックを行う必要があることに注意してください。ただし、これはおそらく宿題であることは理解しています)、sprintf (http://www.cplusplus.com/reference/clibrary/cstdio/sprintf/) を使用します。 :

char lsbuf[1024];
sprintf(lsbuf,"ls -al %s > ls.txt",buffer);
system(lsbuf);

物事を行う適切な方法 (そして、インストラクターがおそらくあなたにそうするように意図している方法) は、コード内で ls、wc などの作業を行うことです。このようなシステムを呼び出すと、まったく新しいクラスのセキュリティ ホールにさらされることになります。

于 2010-11-22T09:13:05.523 に答える
0

現在のコードでは、クライアントによる入力に対して実際には何も行われておらず、動作は説明と一致しません。
これは何をすることになっていますか?:

  for(int i=0;i<1000;i++){
      fscanf(fp,"%c",&buffer[i]);
  }
  fclose(fp);    

これは、入力内の各文字を検索し (ここでは 1000 を使用し、バッファーは 1024 文字になる可能性があるため、最後の 24 文字が欠落しています)、「info.txt」で何回発生したかを返します。NUL 文字 ('\0') も検索することに注意してください。これらの不注意以外には、実際には何もしません。

ファイル内の文字列を見つけて、行番号を操作したいだけだと思いますか?文字列を検索する別の方法が必要です。そのための巧妙なアルゴリズムとそれほど巧妙でないアルゴリズムがいくつかあります。より「野蛮な」アルゴリズムの1つは次のとおりです。

  1. 最初の文字を検索
  2. 次のすべての文字が予想される文字と一致する限り、一部のフラグを「true」のままにします
  3. 一部の文字が一致に違反した場合、最初の文字の次の検索に進みます

これよりも効率的なアルゴリズムがあることに注意してください。

私はあなたのネットワーク設定を精査しませんでした。空白を追加してコードをいくつかの段落に分割するか、ネットワーク設定を別の関数に入れることをお勧めします。

于 2010-11-22T09:18:20.767 に答える
0

まず、bzero の使用は推奨されていないため、避ける必要があります。代わりに memset を使用してください。

関数 fgets は、改行またはファイルの終わりに到達するまで読み取ります。改行は有効な文字であるため、文字列に追加され、ヌル文字が追加されます。

「mytext」と入力してから入力すると、バッファには「mytext\n\0」が含まれます。

現在のコードに基づいて、クライアントからのバッファーを使用していないため、機能していないことは明らかです (改行が追加されたために fgets() の動作が原因であるとは限りません)。

于 2010-11-22T09:18:53.570 に答える