【澳门金沙vip】c语言http诉求深入分析表单内容

cgi.h 复制代码 代码如下:#ifndef
CGI_H#define CGI_H

多年来在做网页爬虫的测验,需求经过apache的access-log来表明爬虫的行为,就悟出了用临近linux的tail命令实现方式来兑现。这里先把代码贴出来:

为了更加好的垂询HTTP公约, 特意谢了八个大约HTTP服务器, 代码独有400行.
因为比很粗大略, 所以功效也可以有一点点高, 并且扶持的特性也十分少, 可是也可以运作,
品质跟Apache大概.

#include stdio.h#include string.h#include stdlib.h

 

=============================================================================================

typedef struct Node{char *name;char *value;struct Node *next;}Node;

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <malloc.h>
#include <sys/stat.h>

#include <fcntl.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <netinet/tcp.h>
#include <errno.h>
#include <sys/ioctl.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

typedef struct Index{Node *head;char *buffer;}Index;

static size_t filesize(const char *filename) {
    struct stat sb;

#define BUFFER_INIT_SIZE 512

Index *get_input();void free_input(Index *);Node *analyze(char
*);Node *analy_a(char *);Node *analy_m(char *, char *);char
*get_value(Node *, char *);char fun1(char);

    if (!stat(filename, &sb))
        return sb.st_size;
    return 0;
}

enum {
    mickey_reading_header_stage,
    mickey_writing_header_stage,
    mickey_writing_body_stage,
    mickey_closing_stage
};

#endif

static void tailf(const char *filename, int lines) {
    char **buffer;
    int head = 0;
    int tail = 0;
    FILE *str;
    int i;

enum {
    mickey_http_ok,
    mickey_http_notfound,
    mickey_http_error
};

get_input.c 复制代码 代码如下:#include
“cgi.h”

    if (!(str = fopen(filename, “r”))) {
        fprintf(stderr, “Cannot open \”%s\” for read\n”, filename);
        perror(“”);
        exit(1);
    }

enum {
    mickey_method_get,
    mickey_method_head,
    mickey_method_unknow
};

Index *get_input(卡塔尔(قطر‎ {//获得表单发送方法char *get_method =
getenv(“REQUEST_METHOD”);Index *input = (Index
*)malloc(sizeof(Index));Node *head;char *buffer;if
(strcmp(get_method,”GET”) == 0) {char *get_str =
getenv(“QUERY_STRING”);if (get_str == NULL || *get_str == 0卡塔尔国 {return
NULL;}//get方法,通过情状变量拿到内容buffer = (char
*)malloc(strlen(get_str) + 1);strcpy(buffer,
get_str卡塔尔;//对剧情开展拆解深入分析,以链表的款式存在head = analy_a(buffer);

    buffer = (char **) malloc(lines * sizeof(*buffer));
    for (i = 0; i < lines; i++)
        buffer[i] = (char *) malloc(BUFSIZ + 1);

typedef struct {
    char *buff;
    int size;
    int free;
} mickey_buffer_t;

} else if (strcmp(get_method,”POST”) == 0){int get_len =
atoi(getenv(“CONTENT_LENGTH”));if (get_len == 0卡塔尔 {return
NULL;}//post方法,通过标准输入读取内容buffer = (char *)malloc(get_len

    while (fgets(buffer[tail], BUFSIZ, str)) {
        if (++tail >= lines) {
            tail = 0;
            head = 1;
        }
    }

typedef struct {
    int sock;
    mickey_buffer_t *request;
    mickey_buffer_t *response;
    int keepalive;
    int method;
    mickey_buffer_t *uri;
    int status;
    int stage;
    FILE *handle;
} mickey_connection_t;

  • 1);memset(buffer,0,get_len + 1);int n =fread(buffer, 1,get_len,
    stdin);if (n != get_len) {fprintf(stderr,”Read error!”State of Qatar;}head =
    analyze(bufferState of Qatar;}//链表头input – head = head;//采纳到的字符串input –
    buffer = buffer;return input;}

    //the method here is very smart, if variable head is set, that is to say the file is longer than 10 lines,
    //and the first line of the last 10 lines is start from the index tail, and the last line is at index tail-1

static int srv_sock;

analyze.c复制代码 代码如下:#include
“cgi.h”//post方法获得的内容实行剖析Node *analyze(char *buffer){//获取内容格式char *c_type = getenv(“CONTENT_TYPE”);char
*bound;fprintf(stderr,”debug:c_type is %s\n”,c_type);if
(strcmp(“application/x-“,c_type卡塔尔(قطر‎ == 0卡塔尔国{//该格式注解获取内容为”name=value”情势return analy_a(buffer);} else if
(strcmp(“text/plain”, c_type卡塔尔 == 0State of Qatar {//此种编码格式暂不研究} else
{//编码格式为multipart/form-data,适用大流量数据传送//获取等号后边的相间符bound
= index(c_type,’=’) + 1;fprintf(stderr,”debug:bound is
%s\n”,bound);return analy_m(buffer, bound);}}

    if (head) {
        for (i = tail; i < lines; i++)
            fputs(buffer[i], stdout);
        for (i = 0; i < tail; i++)
            fputs(buffer[i], stdout);
    } else {
        for (i = head; i < tail; i++)
            fputs(buffer[i], stdout);
    }
    fflush(stdout);

mickey_buffer_t *mickey_buffer_new() {
    mickey_buffer_t *object;
   
    object = malloc(sizeof(*object));
    if (object) {
        object->buff = malloc(BUFFER_INIT_SIZE + 1);
        if (!object->buff) {
            free(object);
            return NULL;
        }
        object->size = BUFFER_INIT_SIZE;
        object->free = BUFFER_INIT_SIZE;
    }
    return object;
}

analy_a.c复制代码 代码如下:#include
“cgi.h”//编码格式为’application/x-‘的从头到尾的经过Node *analy_a(char *buffer卡塔尔(قطر‎{//创设第贰个节点Node *head = (Node *)malloc(sizeof(Node));Node *temp
= head;temp – name = buffer;char *b_temp =
buffer;//通过活动、改换部分字符来分别字符串while (*buffer != 0) {if
(*buffer == ‘=’卡塔尔 {//’=’,则意味name已经竣事,value将起来*b_temp =
0;temp – value = b_temp + 1;}else if (*buffer == ‘+’State of Qatar{//’+’代表空格*b_temp = ‘ ‘;}else if (*buffer == ‘%’){//’%’则紧跟两位十四进制表示的特殊字符*b_temp = fun1(*(buffer + 1))
* 16 + fun1(*(buffer + 2));buffer += 2;}else if (*buffer == ‘&’卡塔尔{//’&’表示value已经收尾,name将在上马*b_temp =
0;//重新申请内存,存款和储蓄新内容地址temp – next = (Node
*)malloc(sizeof(Node));temp = temp – next;temp – name = b_temp +
1;}else {*b_temp =
*buffer;}buffer++;b_temp++;}//最后三个收场符*b_temp = 0;return
head;}

    for (i = 0; i < lines; i++)
        free(buffer[i]);
    free(buffer);
}

int mickey_buffer_append_length(mickey_buffer_t *buf, void *data,
int length) {
    int lack, need = 0;
    char *temp;
   
    if (length > buf->free) {
        lack = length – buf->free;
        while (need < lack)
            need += BUFFER_INIT_SIZE;
        temp = realloc(buf->buff, buf->size + need + 1);
        if (!temp)
            return -1;
        buf->buff = temp;
        buf->size += need;
        buf->free += need;
    }
    memcpy(buf->buff + (buf->size – buf->free), data,
length);
    buf->free -= length;
    buf->buff[buf->size – buf->free] = ‘\0’;
    return 0;
}

analy_m.c复制代码 代码如下:#include
“cgi.h”//编码格式为’multipart/form-data’的从头到尾的经过Node *analy_m(char
*buffer, char *bound) {char *start;char *end;//第一个节点Node *head
= (Node*)malloc(sizeof(Node));Node *temp =
head;fprintf(stderr,”debug:buffer is %s\n”,
buffer卡塔尔国;//伊始深入分析内容,name在多少个双引号之间(详见编码格式卡塔尔temp – name =
index(buffer, ‘”‘卡塔尔国 + 1;end = index(temp – name, ‘”‘卡塔尔(قطر‎;*end =
0;fprintf(stderr,”debug:temp-name is %s\n”, temp –
name卡塔尔;//中间间距了多个”\r\n”temp – value = end + 5;buffer =
strstr(temp – value,
bound卡塔尔;//到下二个间距符,下面间距七个”\r\n”*(buffer – 4) =
0;fprintf(stderr,”debug:temp-valu is %s\n”, temp – value);while ((start
= strstr(buffer,”name=”)) != NULL卡塔尔国{//循环获取name与value地址,直到没有name停止temp – next = (Node
*)malloc(sizeof(Node));temp = temp – next;temp – name = index(start,
‘”‘) + 1;end = index(temp – name, ‘”‘);*end =
0;fprintf(stderr,”debug:temp-name is %s\n”, temp – name);temp – value =
end + 5;buffer = strstr(temp – value, bound);*(buffer – 4) =
0;fprintf(stderr,”debug:temp-valu is %s\n”, temp – value);}return
head;}

int main(int argc, char **argv) {
    char buffer[BUFSIZ];
    size_t osize, nsize;
    FILE *str;
    const char *filename;
    int count;

int mickey_buffer_append(mickey_buffer_t *buf, void *data) {
    return mickey_buffer_append_length(buf, data, strlen((char
*)data));
}