2017-02-18 5 views
0

C-SERVER:
は、外部スクリプトを実行します。 "VVV" に保存されたスクリプトから
応答/スクリプトと "VVV" をクライアントに送信されます。 C-SERVER:HTTPレスポンス欠落している新しい行

fp = popen("/script", "r"); 
fgets(vvv, 500, fp); 

write(client_fd, vvv, sizeof(vvv) - 1); 
close(client_fd); 

内容/スクリプトのnetcatと

#!/bin/sh 
echo -e 'HTTP/1.1 200 OK\r\n'; 

テスト:

echo TEST | nc <ip> <port> 
HTTP/1.1 200 OK 

問題:それは、Webブラウザで動作することができますように、新しい行を含めることができません。

C-SERVER:

#include <arpa/inet.h> 
#include <err.h> 
#include <string.h> 

char inn[100]; 

FILE *fp; 
char vvv[100]; 

int main() 
{ 
    int one = 1, client_fd; 
    struct sockaddr_in svr_addr, cli_addr; 
    socklen_t sin_len = sizeof(cli_addr); 

    int sock = socket(AF_INET, SOCK_STREAM, 0); 
    if (sock < 0) 
    err(1, "can't open socket"); 

    setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, &one, sizeof(int)); 

    int port = 85; 
    svr_addr.sin_family = AF_INET; 
    svr_addr.sin_addr.s_addr = INADDR_ANY; 
    svr_addr.sin_port = htons(port); 

    if (bind(sock, (struct sockaddr *) &svr_addr, sizeof(svr_addr)) == -1) { 
    close(sock); 
    err(1, "Can't bind"); 
    } 

    listen(sock, 5); 
    while (1) { 
    client_fd = accept(sock, (struct sockaddr *) &cli_addr, &sin_len); 
    size_t bytesRead = read(client_fd,inn,sizeof(inn) - 1); 

    fp = popen("/script", "r"); 
    fgets(vvv, 500, fp); 
    printf(vvv); 


    write(client_fd, vvv, sizeof(vvv) - 1); 
    close(client_fd); 
    } 
} 
+0

私はCにはあまりにも新しいです。私は** vvv = vvv + "/ n" **のように何かをする方法を知っていません。 – Vorn3rala

+0

まあ、それは –

+0

あなたのバッファ 'vvv'は100バイトですが、あなたは' fgets'に制限500を与えています、それはなぜですか? –

答えて

0

HTTPヘッダーとコンテンツは、空白の行で区切られていることに注意してください。コンテンツをまったく提供しない場合も同様です。

また、echoは、行の後に改行を追加します。

#!/bin/sh 
printf 'HTTP/1.1 200 OK\r\n'; 
printf '\r\n'; 
printf 'Content'; # provide some content 

しかし、これはあなたがfpから複数の行を読み取る必要があることを今必要があります。代わりにprintfを使用してください。fpからすべての行を読み取るために、追加のループを追加します。

... 

while (1) { 
    client_fd = accept(sock, (struct sockaddr *) &cli_addr, &sin_len); 
    size_t bytesRead = read(client_fd,inn,sizeof(inn) - 1); 

    fp = popen("/script", "r"); 

    while (!feof(fp)) { 
    // be careful here to use `sizeof` instead of the harcoded `500` 
    fgets(vvv, sizeof(vvv), fp); 
    // only write the number of bytes read 
    write(client_fd, vvv, strlen(vvv)); 
    printf(vvv); 
    } 

    close(client_fd); 
} 

... 

はまた、長い行の切り捨てを防ぐためにfreadの代わりfgetsを使用することを検討してください。

0

ここでも、ドキュメントを読んでください。 fgets読み取り:配列は、Sによって指さに

高々一つのストリームからnで指定された文字の数より少ないストリームによって指されます。 改行文字(保持されている)の後に、またはファイルの終わりの後に追加の文字は読み込まれません。ヌル文字は、最後の文字が配列に読み込まれた直後に書き込まれます。

HTTPレスポンスは CRLFの改行を含まなければならない - 最初はステータス行を終了し、第二には、身体からのステータスラインを分離:

HTTP/1.0 200 OK\r\n 
\r\n 

同様のようなこれらの改行を生成する必要がありますあなたのスクリプト:

echo -e 'HTTP/1.1 200 OK\r\n\r\n'; 

しかし、あなたのfgets呼び出しが短い停止します - それは唯一の最初の\n文字まで読み込みます。実際には、すべてのfgetsを使用すべきではありませんが、代わりにEOFが満たされるまで、

fp = popen("/script", "r"); 
while (!feof(fp) && !ferror(fp)) { 
    size_t bytes_read = fread(vvv, 1, sizeof(vvv), fp); 
    if (read) { 
     write(client_fd, vvv, bytes_read); 
    } 
} 
pclose(fp); // must *absolutely* close the pipe with pclose 

のようなものは、(PS HTTP/1.1プロトコルはもう少し複雑で、あなたがサポートすると主張するならば、繰り返しfreadを使用します

関連する問題