...
 
Commits (16)
......@@ -3,7 +3,7 @@
* This program is distributed under the GNU General Public License, version 2.
* A copy of this license is included with this source.
*
* Copyright 2014, Philipp Schafft <lion@lion.leolix.org>
* Copyright 2014-2018, Philipp "ph3-der-loewe" Schafft <lion@lion.leolix.org>,
*/
/* -*- c-basic-offset: 4; indent-tabs-mode: nil; -*- */
......
......@@ -3,7 +3,7 @@
* This program is distributed under the GNU General Public License, version 2.
* A copy of this license is included with this source.
*
* Copyright 2014, Philipp Schafft <lion@lion.leolix.org>
* Copyright 2014-2018, Philipp "ph3-der-loewe" Schafft <lion@lion.leolix.org>,
*/
#ifndef __ACL_H__
......
This diff is collapsed.
......@@ -8,6 +8,7 @@
* oddsock <oddsock@xiph.org>,
* Karl Heyes <karl@xiph.org>
* and others (see AUTHORS for details).
* Copyright 2011-2018, Philipp "ph3-der-loewe" Schafft <lion@lion.leolix.org>,
*/
#ifndef __ADMIN_H__
......@@ -16,6 +17,14 @@
#include <libxml/parser.h>
#include <libxml/tree.h>
/* formats */
typedef enum {
ADMIN_FORMAT_AUTO,
ADMIN_FORMAT_RAW,
ADMIN_FORMAT_TRANSFORMED,
ADMIN_FORMAT_PLAINTEXT
} admin_format_t;
#include "refbuf.h"
#include "client.h"
#include "source.h"
......@@ -27,21 +36,16 @@
#define ADMINTYPE_MOUNT 2
#define ADMINTYPE_HYBRID (ADMINTYPE_GENERAL|ADMINTYPE_MOUNT)
/* formats */
#define RAW 1
#define TRANSFORMED 2
#define PLAINTEXT 3
/* special commands */
#define ADMIN_COMMAND_ERROR (-1)
#define ADMIN_COMMAND_ANY 0 /* for ACL framework */
void admin_handle_request(client_t *client, const char *uri);
void admin_send_response(xmlDocPtr doc,
client_t *client,
int response,
const char *xslt_template);
void admin_send_response(xmlDocPtr doc,
client_t *client,
admin_format_t response,
const char *xslt_template);
void admin_add_listeners_to_mount(source_t *source,
xmlNodePtr parent,
......
......@@ -394,7 +394,7 @@ static void auth_add_client(auth_t *auth, client_t *client, void (*on_no_match)(
auth_user->on_no_match = on_no_match;
auth_user->on_result = on_result;
auth_user->userdata = userdata;
ICECAST_LOG_INFO("adding client %p for authentication on %p", client, auth);
ICECAST_LOG_DEBUG("adding client %p for authentication on %p", client, auth);
queue_auth_client(auth_user);
}
......
......@@ -8,7 +8,7 @@
* oddsock <oddsock@xiph.org>,
* Karl Heyes <karl@xiph.org>
* and others (see AUTHORS for details).
* Copyright 2014, Philipp "ph3-der-loewe" Schafft <lion@lion.leolix.org>,
* Copyright 2014-2018, Philipp "ph3-der-loewe" Schafft <lion@lion.leolix.org>,
*/
#ifndef __AUTH_H__
......@@ -19,7 +19,7 @@
#endif
struct source_tag;
struct auth_tag;
typedef struct auth_tag auth_t;
#include <libxml/xmlmemory.h>
#include <libxml/parser.h>
......@@ -66,7 +66,7 @@ typedef struct auth_client_tag
} auth_client;
typedef struct auth_tag
struct auth_tag
{
/* unique ID */
unsigned long id;
......@@ -113,7 +113,7 @@ typedef struct auth_tag
acl_t *acl;
/* role name for later matching, may be NULL if no role name was given in config */
char *role;
} auth_t;
};
typedef struct auth_stack_tag auth_stack_t;
......
......@@ -191,6 +191,11 @@ static auth_result htpasswd_auth (auth_client *auth_user)
}
htpasswd_recheckfile (htpasswd);
if (htpasswd->users) {
ICECAST_LOG_ERROR("No user list.");
return AUTH_NOMATCH;
}
thread_rwlock_rlock (&htpasswd->file_rwlock);
entry.name = client->username;
if (avl_get_by_key (htpasswd->users, &entry, &result) == 0) {
......@@ -257,8 +262,18 @@ static auth_result htpasswd_adduser (auth_t *auth, const char *username, const c
htpasswd_user entry;
void *result;
if (!state->filename) {
ICECAST_LOG_ERROR("No filename given in options for authenticator.");
return AUTH_FAILED;
}
htpasswd_recheckfile (state);
if (state->users) {
ICECAST_LOG_ERROR("No user list.");
return AUTH_FAILED;
}
thread_rwlock_wlock (&state->file_rwlock);
entry.name = (char*)username;
......@@ -301,6 +316,17 @@ static auth_result htpasswd_deleteuser(auth_t *auth, const char *username)
struct stat file_info;
state = auth->state;
if (!state->filename) {
ICECAST_LOG_ERROR("No filename given in options for authenticator.");
return AUTH_FAILED;
}
if (state->users) {
ICECAST_LOG_ERROR("No user list.");
return AUTH_FAILED;
}
thread_rwlock_wlock (&state->file_rwlock);
passwdfile = fopen(state->filename, "rb");
......@@ -383,8 +409,18 @@ static auth_result htpasswd_userlist(auth_t *auth, xmlNodePtr srcnode)
state = auth->state;
if (!state->filename) {
ICECAST_LOG_ERROR("No filename given in options for authenticator.");
return AUTH_FAILED;
}
htpasswd_recheckfile(state);
if (state->users) {
ICECAST_LOG_ERROR("No user list.");
return AUTH_FAILED;
}
thread_rwlock_rlock(&state->file_rwlock);
node = avl_get_first(state->users);
while (node) {
......
......@@ -28,6 +28,7 @@
#include "common/thread/thread.h"
#include "cfgfile.h"
#include "global.h"
#include "refbuf.h"
#include "client.h"
#include "logging.h"
......@@ -551,6 +552,21 @@ static void config_clear_mount(mount_proxy *mount)
free(mount);
}
static void config_clear_resource(resource_t *resource)
{
resource_t *nextresource;
while (resource) {
nextresource = resource->next;
xmlFree(resource->source);
xmlFree(resource->destination);
xmlFree(resource->bind_address);
xmlFree(resource->vhost);
free(resource);
resource = nextresource;
}
}
listener_t *config_clear_listener(listener_t *listener)
{
listener_t *next = NULL;
......@@ -572,8 +588,6 @@ void config_clear(ice_config_t *c)
*nextrelay;
mount_proxy *mount,
*nextmount;
aliases *alias,
*nextalias;
#ifdef USE_YP
int i;
#endif
......@@ -632,16 +646,7 @@ void config_clear(ice_config_t *c)
mount = nextmount;
}
alias = c->aliases;
while (alias) {
nextalias = alias->next;
xmlFree(alias->source);
xmlFree(alias->destination);
xmlFree(alias->bind_address);
xmlFree(alias->vhost);
free(alias);
alias = nextalias;
}
config_clear_resource(c->resources);
dirnode = c->dir_list;
while (dirnode) {
......@@ -1899,14 +1904,82 @@ static void _parse_directory(xmlDocPtr doc,
configuration->num_yp_directories++;
}
static void _parse_resource(xmlDocPtr doc,
xmlNodePtr node,
ice_config_t *configuration)
{
char *temp;
resource_t *resource,
*current,
*last;
resource = calloc(1, sizeof(resource_t));
if (resource == NULL) {
ICECAST_LOG_ERROR("Can not allocate memory for resource.");
return;
}
resource->next = NULL;
resource->source = (char *)xmlGetProp(node, XMLSTR("source"));
resource->destination = (char *)xmlGetProp(node, XMLSTR("destination"));
if (!resource->destination)
resource->destination = (char *)xmlGetProp(node, XMLSTR("dest"));
if (!resource->source && resource->destination) {
resource->source = resource->destination;
resource->destination = NULL;
} else if (!resource->source && !resource->destination) {
config_clear_resource(resource);
return;
}
temp = (char *)xmlGetProp(node, XMLSTR("port"));
if(temp != NULL) {
resource->port = util_str_to_int(temp, resource->port);
xmlFree(temp);
} else {
resource->port = -1;
}
resource->bind_address = (char *)xmlGetProp(node, XMLSTR("bind-address"));
resource->vhost = (char *)xmlGetProp(node, XMLSTR("vhost"));
temp = (char *)xmlGetProp(node, XMLSTR("omode"));
if (temp) {
resource->omode = config_str_to_omode(temp);
xmlFree(temp);
} else {
resource->omode = OMODE_DEFAULT;
}
temp = (char *)xmlGetProp(node, XMLSTR("prefixmatch"));
if (temp) {
resource->flags |= util_str_to_bool(temp) ? ALIAS_FLAG_PREFIXMATCH : 0;
xmlFree(temp);
}
/* Attach new <resource> as last entry into the global list. */
current = configuration->resources;
last = NULL;
while (current) {
last = current;
current = current->next;
}
if (last) {
last->next = resource;
} else {
configuration->resources = resource;
}
}
static void _parse_paths(xmlDocPtr doc,
xmlNodePtr node,
ice_config_t *configuration)
{
char *temp;
aliases *alias,
*current,
*last;
char *temp;
do {
if (node == NULL)
......@@ -1988,49 +2061,7 @@ static void _parse_paths(xmlDocPtr doc,
if (configuration->adminroot_dir[strlen(configuration->adminroot_dir)-1] == '/')
configuration->adminroot_dir[strlen(configuration->adminroot_dir)-1] = 0;
} else if (xmlStrcmp(node->name, XMLSTR("resource")) == 0 || xmlStrcmp(node->name, XMLSTR("alias")) == 0) {
alias = malloc(sizeof(aliases));
alias->next = NULL;
alias->source = (char *)xmlGetProp(node, XMLSTR("source"));
alias->destination = (char *)xmlGetProp(node, XMLSTR("destination"));
if (!alias->destination)
alias->destination = (char *)xmlGetProp(node, XMLSTR("dest"));
if (!alias->source && alias->destination) {
alias->source = alias->destination;
alias->destination = NULL;
} else if (!alias->source && !alias->destination) {
xmlFree(alias->source);
xmlFree(alias->destination);
free(alias);
continue;
}
temp = (char *)xmlGetProp(node, XMLSTR("port"));
if(temp != NULL) {
alias->port = util_str_to_int(temp, alias->port);
xmlFree(temp);
} else {
alias->port = -1;
}
alias->bind_address = (char *)xmlGetProp(node, XMLSTR("bind-address"));
alias->vhost = (char *)xmlGetProp(node, XMLSTR("vhost"));
temp = (char *)xmlGetProp(node, XMLSTR("omode"));
if (temp) {
alias->omode = config_str_to_omode(temp);
xmlFree(temp);
} else {
alias->omode = OMODE_DEFAULT;
}
current = configuration->aliases;
last = NULL;
while (current) {
last = current;
current = current->next;
}
if(last) {
last->next = alias;
} else {
configuration->aliases = alias;
}
_parse_resource(doc, node, configuration);
}
} while ((node = node->next));
}
......
......@@ -27,7 +27,7 @@ struct _mount_proxy;
#include <libxml/tree.h>
#include "common/thread/thread.h"
#include "common/avl/avl.h"
#include "global.h"
#include "slave.h"
#include "connection.h"
#define XMLSTR(str) ((xmlChar *)(str))
......@@ -155,15 +155,18 @@ typedef struct _mount_proxy {
struct _mount_proxy *next;
} mount_proxy;
typedef struct _aliases {
#define ALIAS_FLAG_PREFIXMATCH 0x0001
typedef struct _resource {
char *source;
char *destination;
int port;
char *bind_address;
char *vhost;
operation_mode omode;
struct _aliases *next;
} aliases;
unsigned int flags;
struct _resource *next;
} resource_t;
typedef struct _listener_t {
struct _listener_t *next;
......@@ -238,7 +241,7 @@ typedef struct ice_config_tag {
char *allowfile;
char *webroot_dir;
char *adminroot_dir;
aliases *aliases;
resource_t *resources;
char *access_log;
char *error_log;
......
......@@ -28,6 +28,7 @@
#include "common/avl/avl.h"
#include "common/httpp/httpp.h"
#include "global.h"
#include "cfgfile.h"
#include "connection.h"
#include "refbuf.h"
......@@ -266,7 +267,7 @@ static inline void _client_send_error(client_t *client, int plain, const icecast
fserve_add_client (client, NULL);
}
void client_send_error_by_id(client_t *client, int id)
void client_send_error_by_id(client_t *client, icecast_error_id_t id)
{
const icecast_error_t *error = error_get_by_id(id);
const char *pref;
......@@ -365,6 +366,26 @@ static inline void client_send_500(client_t *client, const char *message)
client_destroy(client);
}
admin_format_t client_get_admin_format_by_content_negotiation(client_t *client)
{
const char *pref;
if (!client || !client->parser)
return CLIENT_DEFAULT_ADMIN_FORMAT;
pref = util_http_select_best(httpp_getvar(client->parser, "accept"), "text/xml", "text/html", "text/plain", (const char*)NULL);
if (strcmp(pref, "text/xml") == 0) {
return ADMIN_FORMAT_RAW;
} else if (strcmp(pref, "text/html") == 0) {
return ADMIN_FORMAT_TRANSFORMED;
} else if (strcmp(pref, "text/plain") == 0) {
return ADMIN_FORMAT_PLAINTEXT;
} else {
return CLIENT_DEFAULT_ADMIN_FORMAT;
}
}
/* helper function for sending the data to a client */
int client_send_bytes(client_t *client, const void *buf, unsigned len)
{
......
......@@ -19,13 +19,19 @@
#ifndef __CLIENT_H__
#define __CLIENT_H__
typedef struct _client_tag client_t;
#include "errors.h"
#include "connection.h"
#include "refbuf.h"
#include "acl.h"
#include "cfgfile.h"
#include "admin.h"
#include "common/httpp/httpp.h"
#include "common/httpp/encoding.h"
#define CLIENT_DEFAULT_ADMIN_FORMAT ADMIN_FORMAT_TRANSFORMED
typedef enum _protocol_tag {
ICECAST_PROTOCOL_HTTP = 0,
ICECAST_PROTOCOL_SHOUTCAST
......@@ -40,7 +46,7 @@ typedef enum _reuse_tag {
ICECAST_REUSE_UPGRADETLS
} reuse_t;
typedef struct _client_tag
struct _client_tag
{
/* mode of operation for this client */
operation_mode mode;
......@@ -105,13 +111,14 @@ typedef struct _client_tag
/* function to check if refbuf needs updating */
int (*check_buffer)(struct source_tag *source, struct _client_tag *client);
} client_t;
};
int client_create (client_t **c_ptr, connection_t *con, http_parser_t *parser);
void client_destroy(client_t *client);
void client_send_error_by_id(client_t *client, int id);
void client_send_error_by_id(client_t *client, icecast_error_id_t id);
void client_send_101(client_t *client, reuse_t reuse);
void client_send_426(client_t *client, reuse_t reuse);
admin_format_t client_get_admin_format_by_content_negotiation(client_t *client);
int client_send_bytes (client_t *client, const void *buf, unsigned len);
int client_read_bytes (client_t *client, void *buf, unsigned len);
void client_set_queue (client_t *client, refbuf_t *refbuf);
......
......@@ -915,18 +915,6 @@ static void _handle_get_request(client_t *client, char *uri) {
stats_event_inc(NULL, "client_connections");
/* Dispatch legacy admin.cgi requests */
if (strcmp(uri, "/admin.cgi") == 0) {
ICECAST_LOG_DEBUG("Client %p requesting admin interface.", client);
admin_handle_request(client, uri + 1);
return;
} /* Dispatch all admin requests */
else if (strncmp(uri, "/admin/", 7) == 0) {
ICECAST_LOG_DEBUG("Client %p requesting admin interface.", client);
admin_handle_request(client, uri + 7);
return;
}
/* this is a web/ request. let's check if we are allowed to do that. */
if (acl_test_web(client->acl) != ACL_POLICY_ALLOW) {
/* doesn't seem so, sad client :( */
......@@ -1074,10 +1062,10 @@ static void _handle_shoutcast_compatible(client_queue_t *node)
return;
}
/* Handle <alias> lookups here.
/* Handle <resource> lookups here.
*/
static int _handle_aliases(client_t *client, char **uri)
static int _handle_resources(client_t *client, char **uri)
{
const char *http_host = httpp_getvar(client->parser, "host");
char *serverhost = NULL;
......@@ -1087,7 +1075,7 @@ static int _handle_aliases(client_t *client, char **uri)
char *new_uri = NULL;
ice_config_t *config;
listener_t *listen_sock;
aliases *alias;
resource_t *resource;
if (http_host) {
vhost = strdup(http_host);
......@@ -1105,21 +1093,49 @@ static int _handle_aliases(client_t *client, char **uri)
serverport = listen_sock->port;
}
alias = config->aliases;
while (alias) {
if (strcmp(*uri, alias->source) == 0 &&
(alias->port == -1 || alias->port == serverport) &&
(alias->bind_address == NULL || (serverhost != NULL && strcmp(alias->bind_address, serverhost) == 0)) &&
(alias->vhost == NULL || (vhost != NULL && strcmp(alias->vhost, vhost) == 0)) ) {
if (alias->destination)
new_uri = strdup(alias->destination);
if (alias->omode != OMODE_DEFAULT)
client->mode = alias->omode;
ICECAST_LOG_DEBUG("alias has made %s into %s", *uri, new_uri);
break;
resource = config->resources;
/* We now go thru all resources and see if any matches. */
for (; resource; resource = resource->next) {
/* We check for several aspects, if they DO NOT match, we continue with our search. */
/* Check for the URI to match. */
if (resource->flags & ALIAS_FLAG_PREFIXMATCH) {
size_t len = strlen(resource->source);
if (strncmp(*uri, resource->source, len) != 0)
continue;
ICECAST_LOG_DEBUG("Match: *uri='%s', resource->source='%s', len=%zu", *uri, resource->source, len);
} else {
if (strcmp(*uri, resource->source) != 0)
continue;
}
/* Check for the server's port to match. */
if (resource->port != -1 && resource->port != serverport)
continue;
/* Check for the server's bind address to match. */
if (resource->bind_address != NULL && serverhost != NULL && strcmp(resource->bind_address, serverhost) != 0)
continue;
/* Check for the vhost to match. */
if (resource->vhost != NULL && vhost != NULL && strcmp(resource->vhost, vhost) != 0)
continue;
/* Ok, we found a matching entry. */
if (resource->destination) {
if (resource->flags & ALIAS_FLAG_PREFIXMATCH) {
size_t len = strlen(resource->source);
asprintf(&new_uri, "%s%s", resource->destination, (*uri) + len);
} else {
new_uri = strdup(resource->destination);
}
}
alias = alias->next;
if (resource->omode != OMODE_DEFAULT)
client->mode = resource->omode;
ICECAST_LOG_DEBUG("resource has made %s into %s", *uri, new_uri);
break;
}
config_release_config();
......@@ -1135,6 +1151,23 @@ static int _handle_aliases(client_t *client, char **uri)
return 0;
}
static void _handle_admin_request(client_t *client, char *adminuri)
{
ICECAST_LOG_DEBUG("Client %p requesting admin interface.", client);
stats_event_inc(NULL, "client_connections");
switch (client->parser->req_type) {
case httpp_req_get:
admin_handle_request(client, adminuri);
break;
default:
ICECAST_LOG_ERROR("Wrong request type from client");
client_send_error_by_id(client, ICECAST_ERROR_CON_UNKNOWN_REQUEST);
break;
}
}
/* Handle any client that passed the authing process.
*/
static void _handle_authed_client(client_t *client, void *uri, auth_result result)
......@@ -1155,6 +1188,18 @@ static void _handle_authed_client(client_t *client, void *uri, auth_result resul
return;
}
/* Dispatch legacy admin.cgi requests */
if (strcmp(uri, "/admin.cgi") == 0) {
_handle_admin_request(client, uri + 1);
free(uri);
return;
} /* Dispatch all admin requests */
else if (strncmp(uri, "/admin/", 7) == 0) {
_handle_admin_request(client, uri + 7);
free(uri);
return;
}
switch (client->parser->req_type) {
case httpp_req_source:
case httpp_req_put:
......@@ -1377,7 +1422,7 @@ static void _handle_connection(void)
client->mode = config_str_to_omode(httpp_get_query_param(client->parser, "omode"));
if (_handle_aliases(client, &uri) != 0) {
if (_handle_resources(client, &uri) != 0) {
client_destroy (client);
continue;
}
......
......@@ -135,7 +135,7 @@ static const icecast_error_t __errors[] = {
.message = "XSLT problem"}
};
const icecast_error_t * error_get_by_id(int id) {
const icecast_error_t * error_get_by_id(icecast_error_id_t id) {
size_t i;
for (i = 0; i < (sizeof(__errors)/sizeof(*__errors)); i++) {
......
......@@ -9,48 +9,50 @@
#ifndef __ERRORS_H__
#define __ERRORS_H__
#define ICECAST_ERROR_ADMIN_DEST_NOT_RUNNING 1
#define ICECAST_ERROR_ADMIN_METADAT_BADCALL 2
#define ICECAST_ERROR_ADMIN_METADAT_NO_SUCH_ACTION 3
#define ICECAST_ERROR_ADMIN_MISSING_PARAMETER 4
#define ICECAST_ERROR_ADMIN_missing_parameter 5 /* what is this? */
#define ICECAST_ERROR_ADMIN_MOUNT_NOT_ACCEPT_URL_UPDATES 6
#define ICECAST_ERROR_ADMIN_NO_SUCH_DESTINATION 7
#define ICECAST_ERROR_ADMIN_ROLEMGN_ADD_NOSYS 8
#define ICECAST_ERROR_ADMIN_ROLEMGN_DELETE_NOSYS 9
#define ICECAST_ERROR_ADMIN_ROLEMGN_ROLE_NOT_FOUND 10
#define ICECAST_ERROR_ADMIN_SOURCE_DOES_NOT_EXIST 11
#define ICECAST_ERROR_ADMIN_SOURCE_IS_NOT_AVAILABLE 12
#define ICECAST_ERROR_ADMIN_SUPPLIED_MOUNTPOINTS_ARE_IDENTICAL 13
#define ICECAST_ERROR_ADMIN_UNRECOGNISED_COMMAND 14
#define ICECAST_ERROR_AUTH_BUSY 15
#define ICECAST_ERROR_CON_CONTENT_TYPE_NOSYS 16
#define ICECAST_ERROR_CON_INTERNAL_FORMAT_ALLOC_ERROR 17
#define ICECAST_ERROR_CON_MISSING_PASS_PARAMETER 18
#define ICECAST_ERROR_CON_MOUNT_IN_USE 19
#define ICECAST_ERROR_CON_MOUNTPOINT_NOT_STARTING_WITH_SLASH 20
#define ICECAST_ERROR_CON_NO_CONTENT_TYPE_GIVEN 21
#define ICECAST_ERROR_CON_PER_CRED_CLIENT_LIMIT 22
#define ICECAST_ERROR_CON_rejecting_client_for_whatever_reason 23 /* ??? */
#define ICECAST_ERROR_CON_SOURCE_CLIENT_LIMIT 24
#define ICECAST_ERROR_CON_UNIMPLEMENTED 25
#define ICECAST_ERROR_CON_UNKNOWN_REQUEST 26
#define ICECAST_ERROR_CON_UPGRADE_ERROR 27
#define ICECAST_ERROR_FSERV_FILE_NOT_FOUND 28
#define ICECAST_ERROR_FSERV_FILE_NOT_READABLE 29
#define ICECAST_ERROR_FSERV_REQUEST_RANGE_NOT_SATISFIABLE 30
#define ICECAST_ERROR_GEN_BUFFER_REALLOC 31
#define ICECAST_ERROR_GEN_CLIENT_LIMIT 32
#define ICECAST_ERROR_GEN_CLIENT_NEEDS_TO_AUTHENTICATE 33
#define ICECAST_ERROR_GEN_HEADER_GEN_FAILED 34
#define ICECAST_ERROR_GEN_MEMORY_EXHAUSTED 35
#define ICECAST_ERROR_SOURCE_MOUNT_UNAVAILABLE 36
#define ICECAST_ERROR_SOURCE_STREAM_PREPARATION_ERROR 37
#define ICECAST_ERROR_XSLT_PARSE 38
#define ICECAST_ERROR_XSLT_problem 39
typedef enum {
ICECAST_ERROR_ADMIN_DEST_NOT_RUNNING,
ICECAST_ERROR_ADMIN_METADAT_BADCALL,
ICECAST_ERROR_ADMIN_METADAT_NO_SUCH_ACTION,
ICECAST_ERROR_ADMIN_MISSING_PARAMETER,
ICECAST_ERROR_ADMIN_missing_parameter, /* what is this? */
ICECAST_ERROR_ADMIN_MOUNT_NOT_ACCEPT_URL_UPDATES,
ICECAST_ERROR_ADMIN_NO_SUCH_DESTINATION,
ICECAST_ERROR_ADMIN_ROLEMGN_ADD_NOSYS,
ICECAST_ERROR_ADMIN_ROLEMGN_DELETE_NOSYS,
ICECAST_ERROR_ADMIN_ROLEMGN_ROLE_NOT_FOUND,
ICECAST_ERROR_ADMIN_SOURCE_DOES_NOT_EXIST,
ICECAST_ERROR_ADMIN_SOURCE_IS_NOT_AVAILABLE,
ICECAST_ERROR_ADMIN_SUPPLIED_MOUNTPOINTS_ARE_IDENTICAL,
ICECAST_ERROR_ADMIN_UNRECOGNISED_COMMAND,
ICECAST_ERROR_AUTH_BUSY,
ICECAST_ERROR_CON_CONTENT_TYPE_NOSYS,
ICECAST_ERROR_CON_INTERNAL_FORMAT_ALLOC_ERROR,
ICECAST_ERROR_CON_MISSING_PASS_PARAMETER,
ICECAST_ERROR_CON_MOUNT_IN_USE,
ICECAST_ERROR_CON_MOUNTPOINT_NOT_STARTING_WITH_SLASH,
ICECAST_ERROR_CON_NO_CONTENT_TYPE_GIVEN,
ICECAST_ERROR_CON_PER_CRED_CLIENT_LIMIT,
ICECAST_ERROR_CON_rejecting_client_for_whatever_reason, /* ??? */
ICECAST_ERROR_CON_SOURCE_CLIENT_LIMIT,
ICECAST_ERROR_CON_UNIMPLEMENTED,
ICECAST_ERROR_CON_UNKNOWN_REQUEST,
ICECAST_ERROR_CON_UPGRADE_ERROR,
ICECAST_ERROR_FSERV_FILE_NOT_FOUND,
ICECAST_ERROR_FSERV_FILE_NOT_READABLE,
ICECAST_ERROR_FSERV_REQUEST_RANGE_NOT_SATISFIABLE,
ICECAST_ERROR_GEN_BUFFER_REALLOC,
ICECAST_ERROR_GEN_CLIENT_LIMIT,
ICECAST_ERROR_GEN_CLIENT_NEEDS_TO_AUTHENTICATE,
ICECAST_ERROR_GEN_HEADER_GEN_FAILED,
ICECAST_ERROR_GEN_MEMORY_EXHAUSTED,
ICECAST_ERROR_SOURCE_MOUNT_UNAVAILABLE,
ICECAST_ERROR_SOURCE_STREAM_PREPARATION_ERROR,
ICECAST_ERROR_XSLT_PARSE,
ICECAST_ERROR_XSLT_problem
} icecast_error_id_t;
struct icecast_error_tag {
const int id;
const icecast_error_id_t id;
const int http_status;
const char *uuid;
const char *message;
......@@ -58,6 +60,6 @@ struct icecast_error_tag {
typedef struct icecast_error_tag icecast_error_t;
const icecast_error_t * error_get_by_id(int id);
const icecast_error_t * error_get_by_id(icecast_error_id_t id);
#endif /* __ERRORS_H__ */
......@@ -3,7 +3,7 @@
* This program is distributed under the GNU General Public License, version 2.
* A copy of this license is included with this source.
*
* Copyright 2014, Philipp Schafft <lion@lion.leolix.org>
* Copyright 2014-2018, Philipp "ph3-der-loewe" Schafft <lion@lion.leolix.org>,
*/
#ifndef __EVENT_H__
......
......@@ -21,6 +21,7 @@
#endif
#include "event.h"
#include "global.h"
#include "logging.h"
#define CATMODULE "event_exec"
......
......@@ -507,7 +507,7 @@ int fserve_client_create (client_t *httpclient, const char *path)
*eol = '\0';
doc = stats_get_xml (0, reference, httpclient->mode);
free (reference);
admin_send_response (doc, httpclient, TRANSFORMED, xslt_playlist_requested);
admin_send_response (doc, httpclient, ADMIN_FORMAT_TRANSFORMED, xslt_playlist_requested);
xmlFreeDoc(doc);
free (fullpath);
return 0;
......
......@@ -19,15 +19,9 @@
#include "common/thread/thread.h"
#include "common/avl/avl.h"
#include "common/httpp/httpp.h"
#include "connection.h"
#include "refbuf.h"
#include "client.h"
#include "source.h"
#include "format.h"
#include "global.h"
#include "source.h"
ice_global_t global;
......
......@@ -21,6 +21,7 @@
#define ICECAST_VERSION_STRING "Icecast " PACKAGE_VERSION
#include "common/thread/thread.h"
#include "common/avl/avl.h"
#include "slave.h"
#include "common/net/sock.h"
......
......@@ -8,12 +8,14 @@
* oddsock <oddsock@xiph.org>,
* Karl Heyes <karl@xiph.org>
* and others (see AUTHORS for details).
* Copyright 2012-2014, Philipp "ph3-der-loewe" Schafft <lion@lion.leolix.org>,
* Copyright 2012-2018, Philipp "ph3-der-loewe" Schafft <lion@lion.leolix.org>,
*/
#ifndef __SOURCE_H__
#define __SOURCE_H__
typedef struct source_tag source_t;
#include "cfgfile.h"
#include "yp.h"
#include "util.h"
......@@ -23,7 +25,7 @@
#include <stdio.h>
typedef struct source_tag
struct source_tag
{
mutex_t lock;
client_t *client;
......@@ -82,7 +84,7 @@ typedef struct source_tag
playlist_t *history;
} source_t;
};
source_t *source_reserve (const char *mount);
void *source_client_thread (void *arg);
......
......@@ -21,6 +21,7 @@
#include "common/thread/thread.h"
#include "global.h"
#include "curl.h"
#include "connection.h"
#include "refbuf.h"
......