static ret_t
config_server (cherokee_server_t *srv)
{
	ret_t                  ret;
	cherokee_config_node_t conf;
	cherokee_buffer_t      buf       = CHEROKEE_BUF_INIT;
	cherokee_buffer_t      rrd_dir   = CHEROKEE_BUF_INIT;
	cherokee_buffer_t      rrd_bin   = CHEROKEE_BUF_INIT;
	cherokee_buffer_t      fake;

	/* Generate the password
	 */
	if (unsecure == 0) {
		ret = generate_admin_password (&password);
		if (ret != ret_ok)
			return ret;
	}

	/* Configure the embedded server
	 */
	if (scgi_port > 0) {
		ret = find_empty_port (scgi_port, &scgi_port);
	} else {
		ret = remove_old_socket (DEFAULT_UNIX_SOCKET);
	}
	if (ret != ret_ok) {
		return ret_error;
	}

	cherokee_buffer_add_va  (&buf, "server!bind!1!port = %d\n", port);
	cherokee_buffer_add_str (&buf, "server!ipv6 = 1\n");
	cherokee_buffer_add_str (&buf, "server!max_connection_reuse = 0\n");
	cherokee_buffer_add_va  (&buf, "server!iocache = %d\n", iocache);

	if (bind_to) {
		cherokee_buffer_add_va (&buf, "server!bind!1!interface = %s\n", bind_to);
	}

	if (thread_num != -1) {
		cherokee_buffer_add_va (&buf, "server!thread_number = %d\n", thread_num);
	}

	cherokee_buffer_add_str (&buf, "vserver!1!nick = default\n");
	cherokee_buffer_add_va  (&buf, "vserver!1!document_root = %s\n", document_root);

	if (scgi_port <= 0) {
		cherokee_buffer_add_va  (&buf,
					 "source!1!nick = app-logic\n"
					 "source!1!type = interpreter\n"
					 "source!1!timeout = " TIMEOUT "\n"
					 "source!1!host = %s\n"
					 "source!1!interpreter = %s/server.py %s %s %s\n"
					 "source!1!env_inherited = 1\n",
					 DEFAULT_UNIX_SOCKET, document_root,
					 DEFAULT_UNIX_SOCKET, config_file,
					 (debug) ? "-x" : "");

	} else {
		cherokee_buffer_add_va  (&buf,
					 "source!1!nick = app-logic\n"
					 "source!1!type = interpreter\n"
					 "source!1!timeout = " TIMEOUT "\n"
					 "source!1!host = localhost:%d\n"
					 "source!1!interpreter = %s/server.py %d %s %s\n"
					 "source!1!env_inherited = 1\n",
					 scgi_port, document_root,
					 scgi_port, config_file,
					 (debug) ? "-x" : "");
	}

	if (debug) {
		cherokee_buffer_add_str  (&buf, "source!1!debug = 1\n");
	}

	cherokee_buffer_add_str  (&buf,
				  RULE_PRE "1!match = default\n"
				  RULE_PRE "1!handler = scgi\n"
				  RULE_PRE "1!timeout = " TIMEOUT "\n"
				  RULE_PRE "1!handler!balancer = round_robin\n"
				  RULE_PRE "1!handler!balancer!source!1 = 1\n");

	cherokee_buffer_add_str  (&buf, RULE_PRE "1!handler!env!CTK_COOKIE = ");
	generate_admin_password  (&buf);
	cherokee_buffer_add_char (&buf, '\n');

	if (! debug) {
		cherokee_buffer_add_str (&buf, RULE_PRE "1!encoder!gzip = 1\n");
	}

	if ((unsecure == 0) &&
	    (!cherokee_buffer_is_empty (&password)))
	{
		cherokee_buffer_add_va (&buf,
					RULE_PRE "1!auth = authlist\n"
					RULE_PRE "1!auth!methods = digest\n"
					RULE_PRE "1!auth!realm = Cherokee-admin\n"
					RULE_PRE "1!auth!list!1!user = admin\n"
					RULE_PRE "1!auth!list!1!password = %s\n",
					password.buf);
	}

	cherokee_buffer_add_str (&buf,
				 RULE_PRE "2!match = directory\n"
				 RULE_PRE "2!match!directory = /about\n"
				 RULE_PRE "2!handler = server_info\n");

	cherokee_buffer_add_str (&buf,
				 RULE_PRE "3!match = directory\n"
				 RULE_PRE "3!match!directory = /static\n"
				 RULE_PRE "3!handler = file\n"
				 RULE_PRE "3!expiration = time\n"
				 RULE_PRE "3!expiration!time = 30d\n");

	cherokee_buffer_add_va  (&buf,
				 RULE_PRE "4!match = request\n"
				 RULE_PRE "4!match!request = ^/favicon.ico$\n"
				 RULE_PRE "4!document_root = %s/static/images\n"
				 RULE_PRE "4!handler = file\n"
				 RULE_PRE "4!expiration = time\n"
				 RULE_PRE "4!expiration!time = 30d\n",
				 document_root);

	cherokee_buffer_add_va  (&buf,
				 RULE_PRE "5!match = directory\n"
				 RULE_PRE "5!match!directory = /icons_local\n"
				 RULE_PRE "5!handler = file\n"
				 RULE_PRE "5!document_root = %s\n"
				 RULE_PRE "5!expiration = time\n"
				 RULE_PRE "5!expiration!time = 30d\n",
				 CHEROKEE_ICONSDIR);

	cherokee_buffer_add_va  (&buf,
				 RULE_PRE "6!match = directory\n"
				 RULE_PRE "6!match!directory = /CTK\n"
				 RULE_PRE "6!handler = file\n"
				 RULE_PRE "6!document_root = %s/CTK/static\n"
				 RULE_PRE "6!expiration = time\n"
				 RULE_PRE "6!expiration!time = 30d\n",
				 document_root);

	/* Embedded help
	 */
	cherokee_buffer_add_va  (&buf,
				 RULE_PRE "7!match = and\n"
				 RULE_PRE "7!match!left = directory\n"
				 RULE_PRE "7!match!left!directory = /help\n"
				 RULE_PRE "7!match!right = not\n"
				 RULE_PRE "7!match!right!right = extensions\n"
				 RULE_PRE "7!match!right!right!extensions = html\n"
				 RULE_PRE "7!handler = file\n");

	cherokee_buffer_add_va  (&buf,
				 RULE_PRE "8!match = fullpath\n"
				 RULE_PRE "8!match!fullpath!1 = /static/help_404.html\n"
				 RULE_PRE "8!handler = file\n"
				 RULE_PRE "8!document_root = %s\n", document_root);

	cherokee_buffer_add_va  (&buf,
				 RULE_PRE "9!match = and\n"
				 RULE_PRE "9!match!left = directory\n"
				 RULE_PRE "9!match!left!directory = /help\n"
				 RULE_PRE "9!match!right = not\n"
				 RULE_PRE "9!match!right!right = exists\n"
				 RULE_PRE "9!match!right!right!match_any = 1\n"
				 RULE_PRE "9!handler = redir\n"
				 RULE_PRE "9!handler!rewrite!1!show = 1\n"
				 RULE_PRE "9!handler!rewrite!1!substring = /static/help_404.html\n");

	cherokee_buffer_add_va  (&buf,
				 RULE_PRE "10!match = directory\n"
				 RULE_PRE "10!match!directory = /help\n"
				 RULE_PRE "10!match!final = 0\n"
				 RULE_PRE "10!document_root = %s\n", CHEROKEE_DOCDIR);

	/* GZip
	 */
	if (! debug) {
		cherokee_buffer_add_va (&buf,
					RULE_PRE "15!match = extensions\n"
					RULE_PRE "15!match!extensions = css,js,html\n"
					RULE_PRE "15!match!final = 0\n"
					RULE_PRE "15!encoder!gzip = 1\n");
	}

	/* RRDtool graphs
	 */
	cherokee_config_node_init (&conf);
	cherokee_buffer_fake (&fake, config_file, strlen(config_file));

	ret = cherokee_config_reader_parse (&conf, &fake);
	if (ret == ret_ok) {
		cherokee_config_node_copy (&conf, "server!collector!rrdtool_path", &rrd_bin);
		cherokee_config_node_copy (&conf, "server!collector!database_dir", &rrd_dir);
	}

	if (! cherokee_buffer_is_empty (&rrd_bin)) {
		cherokee_buffer_add_va  (&buf,
					 RULE_PRE "20!handler!rrdtool_path = %s\n", rrd_bin.buf);
	}

	if (! cherokee_buffer_is_empty (&rrd_dir)) {
		cherokee_buffer_add_va  (&buf,
					 RULE_PRE "20!handler!database_dir = %s\n", rrd_dir.buf);
	}

	cherokee_buffer_add_str (&buf,
				 RULE_PRE "20!match = directory\n"
				 RULE_PRE "20!match!directory = /graphs\n"
				 RULE_PRE "20!handler = render_rrd\n"
				 RULE_PRE "20!expiration = epoch\n"
				 RULE_PRE "20!expiration!caching = no-cache\n"
				 RULE_PRE "20!expiration!caching!no-store = 1\n");

	cherokee_buffer_add_str (&buf, RULE_PRE "20!document_root = ");
	cherokee_tmp_dir_copy   (&buf);
	cherokee_buffer_add_va  (&buf, "/cherokee/rrd-cache\n");

	/* MIME types
	 */
	cherokee_buffer_add_str (&buf,
				 "mime!text/javascript!extensions = js\n"
				 "mime!text/css!extensions = css\n"
				 "mime!image/png!extensions = png\n"
				 "mime!image/jpeg!extensions = jpeg,jpg\n"
				 "mime!image/svg+xml!extensions = svg,svgz\n"
				 "mime!image/gif!extensions = gif\n");

	ret = cherokee_server_read_config_string (srv, &buf);
	if (ret != ret_ok) {
		PRINT_ERROR_S ("Could not initialize the server\n");
		return ret;
	}

	cherokee_config_node_mrproper (&conf);

	cherokee_buffer_mrproper (&rrd_bin);
	cherokee_buffer_mrproper (&rrd_dir);
	cherokee_buffer_mrproper (&buf);

	return ret_ok;
}
Beispiel #2
0
int main(int argc, char **argv) {
  struct sockaddr_un addr;
  pid_t pid, sid;
  int pipefd[2];
  int clfd;
  char deamonize;
  
  if(argc==2 && !strncmp(argv[1], "-f", 3)) {
    deamonize=0;
  } else {
    deamonize=1;
  }
  
  if(deamonize) {
    if(pipe2(pipefd, O_CLOEXEC)) {
      print( FATAL, "pipe2: %s", strerror(errno) );
      return EXIT_FAILURE;
    }
    
    pid = fork();
    
    if(pid<0) {
      print( FATAL, "fork: %s", strerror(errno) );
      return EXIT_FAILURE;
    } else if(pid) {
      close(pipefd[1]);
      if(!read(pipefd[0], &clfd, 1))
        return EXIT_FAILURE;
      return EXIT_SUCCESS;
    }
    close(pipefd[0]);
  
    umask(0);

    if(open_logfile(LOG_PATH)) {
      print( FATAL, "cannot open logfile");
      return EXIT_FAILURE;
    }

    close(STDIN_FILENO);
    close(STDOUT_FILENO);
    close(STDERR_FILENO);

    set_logger(file_logger);

    sid = setsid();
    if(sid<0) {
      print( FATAL, "setsid: %s", strerror(errno) );
      return EXIT_FAILURE;
    }
  }
  
  if(init_structs())
    return EXIT_FAILURE;
  
  if(load_handlers())
    return EXIT_FAILURE;
  
  if(load_users())
    return EXIT_FAILURE;
  
  if(remove_old_socket())
    return EXIT_FAILURE;
  
  sockfd = socket(AF_UNIX, SOCK_STREAM, 0);
  
  if(sockfd < 0) {
    print( FATAL, "socket: %s", strerror(errno) );
    return EXIT_FAILURE;
  }
  
  if(register_signal_handlers()) {
    close(sockfd);
    return EXIT_FAILURE;
  }
  
  memset(&addr, 0, sizeof(struct sockaddr_un));
  addr.sun_family = AF_UNIX;
  strncpy(addr.sun_path, SOCKET_PATH, sizeof(addr.sun_path)-1);
  if(bind(sockfd, (struct sockaddr*)&addr, sizeof(addr))) {
    print( FATAL, "bind: %s", strerror(errno) );
    close(sockfd);
    unlink(SOCKET_PATH);
    return EXIT_FAILURE;
  }
  
  if(listen(sockfd, 5)) {
    print( FATAL, "listen: %s", strerror(errno) );
    close(sockfd);
    unlink(SOCKET_PATH);
    return EXIT_FAILURE;
  }
  
  if(start_reaper()) {
    close(sockfd);
    unlink(SOCKET_PATH);
    return EXIT_FAILURE;
  }
  
#ifndef NDEBUG
  chmod(SOCKET_PATH, 0666);
#endif
  
  if(deamonize) {
    if(write(pipefd[1], "!", 1) != 1) {
      print( FATAL, "cannot notify that daemon started" );
      return EXIT_FAILURE;
    }
    close(pipefd[1]);
  }
  
  while(1) {
    if((clfd=accept(sockfd, NULL, NULL)) < 0) {
      if(errno == EINVAL) {
#ifndef NDEBUG
        print( DEBUG, "socket closed" );
#endif
      }
      print( ERROR, "accept: %s", strerror(errno) );
      break;
    }
    
    if(serve_new_client(clfd)) {
      print( WARNING, "cannot serve new connection" );
      close(clfd);
    }
  }
  
  unlink(SOCKET_PATH);
  
  close_connections();
  
  stop_reaper();
  
  destroy_structs();
  
  unload_users();
  unload_handlers();
  
  return EXIT_SUCCESS;
}