⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 http-server.c

📁 Sofia SIP is an open-source SIP User-Agent library, compliant with the IETF RFC3261 specification.
💻 C
字号:
/* * This file is part of the Sofia-SIP package * * Copyright (C) 2005 Nokia Corporation. * * Contact: Pekka Pessi <pekka.pessi@nokia.com> * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public License * as published by the Free Software Foundation; either version 2.1 of * the License, or (at your option) any later version. * * This library is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public * License along with this library; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA * 02110-1301 USA * *//**@nofile http-server.c * @brief Test HTTP server * * @author Pekka Pessi <Pekka.Pessi@nokia.com>. * * @date Created: Sat Oct 19 02:56:23 2002 ppessi * */#include "config.h"#include <stddef.h>#include <stdlib.h>#include <string.h>#include <stdio.h>#include <assert.h>#if HAVE_SIGNAL#include <signal.h>#endiftypedef struct context_s context_t;#define NTH_SITE_MAGIC_T context_t#define SU_ROOT_MAGIC_T context_t#include <sofia-sip/nth.h>#include <sofia-sip/tport_tag.h>#include <sofia-sip/http_header.h>struct context_s {  su_home_t   	  c_home[1];  su_root_t   	 *c_root;  nth_site_t 	 *c_site;  char const     *c_server;  char const     *c_expires;  char const     *c_content_type;  http_content_length_t *c_content_length;  msg_payload_t *c_body;};char const name[] = "http-server";staticvoid usage(int rc){  fprintf(rc ? stderr : stdout,	  "usage: %s OPTIONS url [content]\n",	  name	  );  exit(rc);}static int request(context_t *context,		   nth_site_t *site,		   nth_request_t *req,		   http_t const *http,		   char const *path);su_msg_r server_intr_msg = SU_MSG_R_INIT;#if HAVE_SIGNALstatic RETSIGTYPE server_intr_handler(int signum);#endifstatic void server_break(context_t *c, su_msg_r msg, su_msg_arg_t *arg);static msg_payload_t *read_payload(su_home_t *home, char const *fname);static msg_payload_t *fread_payload(su_home_t *home, FILE *f);int main(int argc, char *argv[]){  su_home_t *home;  context_t *c, context[1] = {{{SU_HOME_INIT(context)}}};  char *o_url = NULL, *o_body = NULL;  int o_extra = 0;  int o_timeout = 300;  char *s;  c = context;  su_init();  su_home_init(home = context->c_home);#define MATCH(s, v) \      ((strncmp(s, v, strlen(v)) == 0))#define MATCH1(s, v) \      ((strncmp(s, v, strlen(v)) == 0) && \       (s = (s[strlen(v)] ? s + strlen(v) : argv++[1])))#define MATCH2(s, v) \      ((strncmp(s, v, strlen(v)) == 0) && \       (s[strlen(v)] == '=' ? (s = s + strlen(v) + 1) : (s = argv++[1])))  while ((s = argv++[1])) {    if (*s != '-') break;    s++;    if (MATCH2(s, "-expires")) 	         { c->c_expires = s; 	    continue; }    else if (MATCH2(s, "-tcp-timeout"))  { o_timeout = strtoul(s, &s, 0); continue; }    else if (MATCH2(s, "-ct"))           { c->c_content_type = s;   continue; }    else if (MATCH2(s, "-content-type")) { c->c_content_type = s;   continue; }    else if (MATCH2(s, "-server"))       { c->c_server = s;         continue; }    else if (MATCH(s, "-help"))          { usage(0);                continue; }    else if (MATCH(s, "x")||MATCH(s, "-extra")) { o_extra = 1;      continue; }    else      usage(2);  }  if (!(o_url = s))    usage(1);  else    o_body = argv++[1];  context->c_root = su_root_create(context);  context->c_body = read_payload(context->c_home, o_body);  if (!context->c_body) {    perror("contents");    exit(1);  }  context->c_content_length =    msg_content_length_create(context->c_home, context->c_body->pl_len);  su_msg_create(server_intr_msg,		su_root_task(context->c_root),		su_root_task(context->c_root),		server_break, 0);#if HAVE_SIGNAL  signal(SIGINT, server_intr_handler);#if HAVE_SIGQUIT  signal(SIGQUIT, server_intr_handler);  signal(SIGHUP, server_intr_handler);#endif#endif  if (context->c_root) {    context->c_site =      nth_site_create(NULL,	             /* This is a top-level site */		      request, context,		      (url_string_t *)o_url,		      NTHTAG_ROOT(context->c_root),		      TPTAG_TIMEOUT(o_timeout * 1000),		      TAG_END());    if (context->c_site) {      su_root_run(context->c_root);      nth_site_destroy(context->c_site);    }    su_root_destroy(context->c_root);  }  su_deinit();  return 0;}static void server_break(context_t *c, su_msg_r msg, su_msg_arg_t *arg){  fprintf(stderr, "%s: received signal, exiting\n", name);  su_root_break(c->c_root);}static RETSIGTYPE server_intr_handler(int signum){  su_msg_send(server_intr_msg);}static int request(context_t *c,		   nth_site_t *site,		   nth_request_t *req,		   http_t const *http,		   char const *path){  fprintf(stderr, "request to /%s\n", path);  if (path && strlen(path))    return 404;  if (http->http_request->rq_method != http_method_get) {    nth_request_treply(req, HTTP_405_NOT_ALLOWED,		       HTTPTAG_ALLOW_STR("GET"),		       TAG_END());    return 405;  }  nth_request_treply(req, HTTP_200_OK,		     HTTPTAG_SERVER_STR(c->c_server),		     HTTPTAG_EXPIRES_STR(c->c_expires),		     HTTPTAG_CONTENT_TYPE_STR(c->c_content_type),		     HTTPTAG_CONTENT_LENGTH(c->c_content_length),		     HTTPTAG_PAYLOAD(c->c_body),		     TAG_END());  return 200;}/** Read message body from named file. * * The function read_payload() reads the contents to a SIP payload * structure from a the named file. If @a fname is NULL, the payload * contents are read from standard input. */msg_payload_t *read_payload(su_home_t *home, char const *fname){  FILE *f;  msg_payload_t *pl;  if (fname == NULL || strcmp(fname, "-") == 0)    f = stdin, fname = "<stdin>";  else    f = fopen(fname, "rb");  if (f == NULL)    return NULL;  pl = fread_payload(home, f);  if (f != stdin)    fclose(f);  return pl;}msg_payload_t *fread_payload(su_home_t *home, FILE *f){  msg_payload_t *pl;  int n;  char *buf;  off_t used, size;  if (f == NULL) {    errno = EINVAL;    return NULL;  }  pl = msg_payload_create(home, NULL, 0);  if (pl == NULL)    return NULL;  /* Read block by block */  used = 0;  size = 4096;  buf = malloc(size);  while (buf) {    n = fread(buf + used, 1, size - used, f);    used += n;    if (n < size - used) {      if (feof(f))	;      else if (ferror(f))	buf = NULL;      break;    }    buf = realloc(buf, size = 2 * size);  }  if (buf == NULL) {    perror("fread_payload: realloc");    return NULL;  }  if (used < size)    buf[used] = '\0';  pl->pl_common->h_data = pl->pl_data = buf;  pl->pl_common->h_len = pl->pl_len = used;  return pl;}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -