SOURCES: lighttpd-mod_h264_streaming.patch - updated to version 2
glen
glen at pld-linux.org
Mon Jan 26 20:09:54 CET 2009
Author: glen Date: Mon Jan 26 19:09:54 2009 GMT
Module: SOURCES Tag: HEAD
---- Log message:
- updated to version 2
---- Files affected:
SOURCES:
lighttpd-mod_h264_streaming.patch (1.1 -> 1.2)
---- Diffs:
================================================================
Index: SOURCES/lighttpd-mod_h264_streaming.patch
diff -u SOURCES/lighttpd-mod_h264_streaming.patch:1.1 SOURCES/lighttpd-mod_h264_streaming.patch:1.2
--- SOURCES/lighttpd-mod_h264_streaming.patch:1.1 Tue Oct 23 22:48:42 2007
+++ SOURCES/lighttpd-mod_h264_streaming.patch Mon Jan 26 20:09:48 2009
@@ -1,4 +1,3 @@
-diff -ur -x '*.m4' -x ltmain.sh -x install-sh -x depcomp -x Makefile.in -x compile -x 'config.*' -x configure -x missing -x mkinstalldirs -x autom4te.cache -Nur -x .svn lighttpd-1.4.18/src/Makefile.am lighttpd-mod_h264_streaming-1.4.18/src/Makefile.am
--- lighttpd-1.4.18/src/Makefile.am 2007-09-03 01:23:53.000000000 +0300
+++ lighttpd-mod_h264_streaming-1.4.18/src/Makefile.am 2007-10-23 23:42:37.736979478 +0300
@@ -77,6 +77,11 @@
@@ -13,30 +12,16 @@
lib_LTLIBRARIES += mod_evasive.la
mod_evasive_la_SOURCES = mod_evasive.c
mod_evasive_la_LDFLAGS = -module -export-dynamic -avoid-version -no-undefined
-diff -ur -x '*.m4' -x ltmain.sh -x install-sh -x depcomp -x Makefile.in -x compile -x 'config.*' -x configure -x missing -x mkinstalldirs -x autom4te.cache -Nur -x .svn lighttpd-1.4.18/src/mod_h264_streaming.c lighttpd-mod_h264_streaming-1.4.18/src/mod_h264_streaming.c
---- lighttpd-1.4.18/src/mod_h264_streaming.c 1970-01-01 03:00:00.000000000 +0300
-+++ lighttpd-mod_h264_streaming-1.4.18/src/mod_h264_streaming.c 2007-10-23 23:42:37.696978564 +0300
-@@ -0,0 +1,467 @@
+--- /dev/null 2008-11-04 20:33:38.146691408 +0200
++++ lighttpd-1.4.18/src/mod_h264_streaming.c 2009-01-26 20:59:51.385271731 +0200
+@@ -0,0 +1,337 @@
+/*******************************************************************************
+ mod_h264_streaming.c
+
+ mod_h264_streaming - A lighttpd plugin for pseudo-streaming Quicktime/MPEG4 files.
+ http://h264.code-shop.com
+
-+ Copyright (C) 2007 CodeShop B.V.
-+
-+ This program is free software: you can redistribute it and/or modify
-+ it under the terms of the GNU General Public License as published by
-+ the Free Software Foundation, either version 3 of the License, or
-+ (at your option) any later version.
-+
-+ This program 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 General Public License for more details.
-+
-+ You should have received a copy of the GNU General Public License
-+ along with this program. If not, see <http://www.gnu.org/licenses/>.
++ Copyright (C) 2007-2009 CodeShop B.V.
+******************************************************************************/
+
+#include <ctype.h>
@@ -57,463 +42,357 @@
+#include "config.h"
+#endif
+
++#include "moov.h"
++
+/* plugin config for all request/connections */
+
+typedef struct {
-+ array *extensions;
++ array *extensions;
+} plugin_config;
+
+typedef struct {
-+ PLUGIN_DATA;
++ PLUGIN_DATA;
+
-+ buffer *query_str;
-+ array *get_params;
++ buffer *query_str;
++ array *get_params;
+
-+ plugin_config **config_storage;
++ plugin_config **config_storage;
+
-+ plugin_config conf;
++ plugin_config conf;
+} plugin_data;
+
+/* init the plugin data */
+INIT_FUNC(mod_h264_streaming_init) {
-+ plugin_data *p;
++ plugin_data *p;
+
-+ p = calloc(1, sizeof(*p));
++ p = calloc(1, sizeof(*p));
+
-+ p->query_str = buffer_init();
-+ p->get_params = array_init();
++ p->query_str = buffer_init();
++ p->get_params = array_init();
+
-+ return p;
++ return p;
+}
+
+/* detroy the plugin data */
+FREE_FUNC(mod_h264_streaming_free) {
-+ plugin_data *p = p_d;
++ plugin_data *p = p_d;
+
-+ UNUSED(srv);
++ UNUSED(srv);
+
-+ if (!p) return HANDLER_GO_ON;
++ if (!p) return HANDLER_GO_ON;
+
-+ if (p->config_storage) {
-+ size_t i;
++ if (p->config_storage) {
++ size_t i;
+
-+ for (i = 0; i < srv->config_context->used; i++) {
-+ plugin_config *s = p->config_storage[i];
++ for (i = 0; i < srv->config_context->used; i++) {
++ plugin_config *s = p->config_storage[i];
+
-+ if (!s) continue;
++ if (!s) continue;
+
-+ array_free(s->extensions);
++ array_free(s->extensions);
+
-+ free(s);
-+ }
-+ free(p->config_storage);
-+ }
++ free(s);
++ }
++ free(p->config_storage);
++ }
+
-+ buffer_free(p->query_str);
-+ array_free(p->get_params);
++ buffer_free(p->query_str);
++ array_free(p->get_params);
+
-+ free(p);
++ free(p);
+
-+ return HANDLER_GO_ON;
++ return HANDLER_GO_ON;
+}
+
+/* handle plugin config and check values */
+
+SETDEFAULTS_FUNC(mod_h264_streaming_set_defaults) {
-+ plugin_data *p = p_d;
-+ size_t i = 0;
++ plugin_data *p = p_d;
++ size_t i = 0;
+
-+ config_values_t cv[] = {
-+ { "h264-streaming.extensions", NULL, T_CONFIG_ARRAY, T_CONFIG_SCOPE_CONNECTION }, /* 0 */
-+ { NULL, NULL, T_CONFIG_UNSET, T_CONFIG_SCOPE_UNSET }
-+ };
++ config_values_t cv[] = {
++ { "h264-streaming.extensions", NULL, T_CONFIG_ARRAY, T_CONFIG_SCOPE_CONNECTION }, /* 0 */
++ { NULL, NULL, T_CONFIG_UNSET, T_CONFIG_SCOPE_UNSET }
++ };
+
-+ if (!p) return HANDLER_ERROR;
++ if (!p) return HANDLER_ERROR;
+
-+ p->config_storage = calloc(1, srv->config_context->used * sizeof(specific_config *));
++ p->config_storage = calloc(1, srv->config_context->used * sizeof(specific_config *));
+
-+ for (i = 0; i < srv->config_context->used; i++) {
-+ plugin_config *s;
++ for (i = 0; i < srv->config_context->used; i++) {
++ plugin_config *s;
+
-+ s = calloc(1, sizeof(plugin_config));
-+ s->extensions = array_init();
++ s = calloc(1, sizeof(plugin_config));
++ s->extensions = array_init();
+
-+ cv[0].destination = s->extensions;
++ cv[0].destination = s->extensions;
+
-+ p->config_storage[i] = s;
++ p->config_storage[i] = s;
+
-+ if (0 != config_insert_values_global(srv, ((data_config *)srv->config_context->data[i])->value, cv)) {
-+ return HANDLER_ERROR;
-+ }
-+ }
++ if (0 != config_insert_values_global(srv, ((data_config *)srv->config_context->data[i])->value, cv)) {
++ return HANDLER_ERROR;
++ }
++ }
+
-+ return HANDLER_GO_ON;
++ return HANDLER_GO_ON;
+}
+
+#define PATCH(x) \
-+ p->conf.x = s->x;
++ p->conf.x = s->x;
+static int mod_h264_streaming_patch_connection(server *srv, connection *con, plugin_data *p) {
-+ size_t i, j;
-+ plugin_config *s = p->config_storage[0];
-+
-+ PATCH(extensions);
++ size_t i, j;
++ plugin_config *s = p->config_storage[0];
+
-+ /* skip the first, the global context */
-+ for (i = 1; i < srv->config_context->used; i++) {
-+ data_config *dc = (data_config *)srv->config_context->data[i];
-+ s = p->config_storage[i];
-+
-+ /* condition didn't match */
-+ if (!config_check_cond(srv, con, dc)) continue;
-+
-+ /* merge config */
-+ for (j = 0; j < dc->value->used; j++) {
-+ data_unset *du = dc->value->data[j];
-+
-+ if (buffer_is_equal_string(du->key, CONST_STR_LEN("h264-streaming.extensions"))) {
-+ PATCH(extensions);
-+ }
-+ }
-+ }
++ PATCH(extensions);
+
-+ return 0;
-+}
-+#undef PATCH
-+
-+static int split_get_params(array *get_params, buffer *qrystr) {
-+ size_t is_key = 1;
-+ size_t i;
-+ char *key = NULL, *val = NULL;
++ /* skip the first, the global context */
++ for (i = 1; i < srv->config_context->used; i++) {
++ data_config *dc = (data_config *)srv->config_context->data[i];
++ s = p->config_storage[i];
+
-+ key = qrystr->ptr;
++ /* condition didn't match */
++ if (!config_check_cond(srv, con, dc)) continue;
+
-+ /* we need the \0 */
-+ for (i = 0; i < qrystr->used; i++) {
-+ switch(qrystr->ptr[i]) {
-+ case '=':
-+ if (is_key) {
-+ val = qrystr->ptr + i + 1;
++ /* merge config */
++ for (j = 0; j < dc->value->used; j++) {
++ data_unset *du = dc->value->data[j];
+
-+ qrystr->ptr[i] = '\0';
++ if (buffer_is_equal_string(du->key, CONST_STR_LEN("h264-streaming.extensions"))) {
++ PATCH(extensions);
++ }
++ }
++ }
+
-+ is_key = 0;
-+ }
++ return 0;
++}
++#undef PATCH
+
-+ break;
-+ case '&':
-+ case '\0': /* fin symbol */
-+ if (!is_key) {
-+ data_string *ds;
-+ /* we need at least a = since the last & */
++static int split_get_params(array *get_params, buffer *qrystr) {
++ size_t is_key = 1;
++ size_t i;
++ char *key = NULL, *val = NULL;
++
++ key = qrystr->ptr;
++
++ /* we need the \0 */
++ for (i = 0; i < qrystr->used; i++) {
++ switch(qrystr->ptr[i]) {
++ case '=':
++ if (is_key) {
++ val = qrystr->ptr + i + 1;
+
-+ /* terminate the value */
-+ qrystr->ptr[i] = '\0';
++ qrystr->ptr[i] = '\0';
+
-+ if (NULL == (ds = (data_string *)array_get_unused_element(get_params, TYPE_STRING))) {
-+ ds = data_string_init();
-+ }
-+ buffer_copy_string_len(ds->key, key, strlen(key));
-+ buffer_copy_string_len(ds->value, val, strlen(val));
++ is_key = 0;
++ }
+
-+ array_insert_unique(get_params, (data_unset *)ds);
-+ }
++ break;
++ case '&':
++ case '\0': /* fin symbol */
++ if (!is_key) {
++ data_string *ds;
++ /* we need at least a = since the last & */
+
-+ key = qrystr->ptr + i + 1;
-+ val = NULL;
-+ is_key = 1;
-+ break;
-+ }
-+ }
++ /* terminate the value */
++ qrystr->ptr[i] = '\0';
+
-+ return 0;
-+}
++ if (NULL == (ds = (data_string *)array_get_unused_element(get_params, TYPE_STRING))) {
++ ds = data_string_init();
++ }
++ buffer_copy_string_len(ds->key, key, strlen(key));
++ buffer_copy_string_len(ds->value, val, strlen(val));
+
-+extern unsigned int moov_seek(unsigned char* moov_data, unsigned int size,
-+ float start_time,
-+ unsigned int* mdat_start, unsigned int* mdat_size,
-+ unsigned int offset);
++ array_insert_unique(get_params, (data_unset *)ds);
++ }
+
-+void write_char(unsigned char* outbuffer, int value)
-+{
-+ outbuffer[0] = (unsigned char)(value);
-+}
++ key = qrystr->ptr + i + 1;
++ val = NULL;
++ is_key = 1;
++ break;
++ }
++ }
+
-+void write_int32(unsigned char* outbuffer, long value)
-+{
-+ outbuffer[0] = (unsigned char)((value >> 24) & 0xff);
-+ outbuffer[1] = (unsigned char)((value >> 16) & 0xff);
-+ outbuffer[2] = (unsigned char)((value >> 8) & 0xff);
-+ outbuffer[3] = (unsigned char)((value >> 0) & 0xff);
++ return 0;
+}
+
-+struct atom_t
-+{
-+ unsigned char type_[4];
-+ unsigned int size_;
-+ unsigned int start_;
-+ unsigned int end_;
-+};
-+
-+#define ATOM_PREAMBLE_SIZE 8
-+
-+unsigned int atom_header_size(unsigned char* atom_bytes)
-+{
-+ return (atom_bytes[0] << 24) +
-+ (atom_bytes[1] << 16) +
-+ (atom_bytes[2] << 8) +
-+ (atom_bytes[3]);
-+}
++URIHANDLER_FUNC(mod_h264_streaming_path_handler) {
++ plugin_data *p = p_d;
++ int s_len;
++ size_t k;
++
++ UNUSED(srv);
++
++ if (buffer_is_empty(con->physical.path)) return HANDLER_GO_ON;
++
++ mod_h264_streaming_patch_connection(srv, con, p);
++
++ s_len = con->physical.path->used - 1;
++
++ for (k = 0; k < p->conf.extensions->used; k++) {
++ data_string *ds = (data_string *)p->conf.extensions->data[k];
++ int ct_len = ds->value->used - 1;
++
++ if (ct_len > s_len) continue;
++ if (ds->value->used == 0) continue;
++
++ if (0 == strncmp(con->physical.path->ptr + s_len - ct_len, ds->value->ptr, ct_len)) {
++ data_string *get_param;
++ stat_cache_entry *sce = NULL;
++ double start = 0.0;
++ double end = 0.0;
++ char *err = NULL;
++ int client_is_flash = 0;
++
++ array_reset(p->get_params);
++ buffer_copy_string_buffer(p->query_str, con->uri.query);
++ split_get_params(p->get_params, p->query_str);
++
++ /* if there is a start=[0-9]+ in the header use it as start,
++ * otherwise send the full file */
++ if (NULL != (get_param = (data_string *)array_get_element(p->get_params, "start")))
++ {
++ /* check if it is a number */
++ start = strtod(get_param->value->ptr, &err);
++ if (*err != '\0') {
++ return HANDLER_GO_ON;
++ }
++ if (start < 0) return HANDLER_GO_ON;
++ }
+
-+int atom_read_header(FILE* infile, struct atom_t* atom)
-+{
-+ unsigned char atom_bytes[ATOM_PREAMBLE_SIZE];
++ /* if there is an end=[0-9]+ in the header use it as end */
++ if (NULL != (get_param = (data_string *)array_get_element(p->get_params, "end")))
++ {
++ /* check if it is a number */
++ end = strtod(get_param->value->ptr, &err);
++ if (*err != '\0') {
++ return HANDLER_GO_ON;
++ }
++ if (end < 0 || start >= end) return HANDLER_GO_ON;
++ }
+
-+ atom->start_ = ftell(infile);
++ if (NULL != (get_param = (data_string *)array_get_element(p->get_params, "client")))
++ {
++ client_is_flash = starts_with(get_param->value->ptr, "FLASH");
++ }
+
-+ fread(atom_bytes, ATOM_PREAMBLE_SIZE, 1, infile);
-+ memcpy(&atom->type_[0], &atom_bytes[4], 4);
-+ atom->size_ = atom_header_size(atom_bytes);
-+ atom->end_ = atom->start_ + atom->size_;
++ /* get file info */
++ if (HANDLER_GO_ON != stat_cache_get_entry(srv, con, con->physical.path, &sce)) {
++ return HANDLER_GO_ON;
++ }
+
-+ return 1;
-+}
++ /* we are safe now, let's build a h264 header */
++ {
++ {
++ unsigned int filesize = sce->st.st_size;
+
-+void atom_write_header(unsigned char* outbuffer, struct atom_t* atom)
-+{
-+ int i;
-+ write_int32(outbuffer, atom->size_);
-+ for(i = 0; i != 4; ++i)
-+ write_char(outbuffer + 4 + i, atom->type_[i]);
-+}
++ void* mp4_header;
++ uint32_t mp4_header_size;
++ uint64_t mdat_offset;
++ uint64_t mdat_size;
++
++ int result = mp4_split(con->physical.path->ptr, filesize, start, end,
++ &mp4_header, &mp4_header_size,
++ &mdat_offset, &mdat_size, client_is_flash);
+
-+int atom_is(struct atom_t const* atom, const char* type)
-+{
-+ return (atom->type_[0] == type[0] &&
-+ atom->type_[1] == type[1] &&
-+ atom->type_[2] == type[2] &&
-+ atom->type_[3] == type[3])
-+ ;
-+}
++ if(result)
++ {
++ buffer* b = chunkqueue_get_append_buffer(con->write_queue);
++ buffer_append_memory(b, mp4_header, mp4_header_size);
++ b->used++; /* add virtual \0 */
+
-+void atom_skip(FILE* infile, struct atom_t const* atom)
-+{
-+ fseek(infile, atom->end_, SEEK_SET);
-+}
++ http_chunk_append_file(srv, con, con->physical.path,
++ mdat_offset, mdat_size);
++ }
+
-+void atom_print(struct atom_t const* atom)
-+{
-+ printf("Atom(%c%c%c%c,%d)\n", atom->type_[0], atom->type_[1],
-+ atom->type_[2], atom->type_[3], atom->size_);
-+}
++ if(mp4_header)
++ {
++ free(mp4_header);
++ }
+
++ if(!result)
++ {
++ return HANDLER_GO_ON;
++ }
++ }
++ }
+
-+URIHANDLER_FUNC(mod_h264_streaming_path_handler) {
-+ plugin_data *p = p_d;
-+ int s_len;
-+ size_t k;
-+
-+ UNUSED(srv);
-+
-+ if (buffer_is_empty(con->physical.path)) return HANDLER_GO_ON;
-+
-+ mod_h264_streaming_patch_connection(srv, con, p);
-+
-+ s_len = con->physical.path->used - 1;
-+
-+ for (k = 0; k < p->conf.extensions->used; k++) {
-+ data_string *ds = (data_string *)p->conf.extensions->data[k];
-+ int ct_len = ds->value->used - 1;
-+
-+ if (ct_len > s_len) continue;
-+ if (ds->value->used == 0) continue;
-+
-+ if (0 == strncmp(con->physical.path->ptr + s_len - ct_len, ds->value->ptr, ct_len)) {
-+ data_string *get_param;
-+ stat_cache_entry *sce = NULL;
-+ buffer *b;
-+ double start;
-+ char *err = NULL;
-+ /* if there is a start=[0-9]+ in the header use it as start,
-+ * otherwise send the full file */
-+
-+ array_reset(p->get_params);
-+ buffer_copy_string_buffer(p->query_str, con->uri.query);
-+ split_get_params(p->get_params, p->query_str);
-+
-+ if (NULL == (get_param = (data_string *)array_get_element(p->get_params, "start"))) {
-+ return HANDLER_GO_ON;
-+ }
-+
-+ /* too short */
-+// if (get_param->value->used < 2) return HANDLER_GO_ON;
-+
-+ /* check if it is a number */
-+// start = strtol(get_param->value->ptr, &err, 10);
-+ start = strtod(get_param->value->ptr, &err);
-+ if (*err != '\0') {
-+ return HANDLER_GO_ON;
-+ }
-+
-+// if (start <= 0) return HANDLER_GO_ON;
-+ if (start < 0) return HANDLER_GO_ON;
-+
-+ /* check if start is > filesize */
-+ if (HANDLER_GO_ON != stat_cache_get_entry(srv, con, con->physical.path, &sce)) {
-+ return HANDLER_GO_ON;
-+ }
-+
-+// if (start > sce->st.st_size) {
-+// return HANDLER_GO_ON;
-+// }
-+
-+ /* we are safe now, let's build a h264 header */
-+ b = chunkqueue_get_append_buffer(con->write_queue);
-+#if 0
-+ BUFFER_COPY_STRING_CONST(b, "FLV\x1\x1\0\0\0\x9\0\0\0\x9");
-+ http_chunk_append_file(srv, con, con->physical.path, start, sce->st.st_size - start);
-+#else
-+ {
-+ FILE* infile;
-+ struct atom_t ftyp_atom;
-+ struct atom_t moov_atom;
-+ struct atom_t mdat_atom;
-+ unsigned char* moov_data = 0;
-+ unsigned char* ftyp_data = 0;
-+
-+ infile = fopen(con->physical.path->ptr, "rb");
-+ if(!infile) {
-+ return HANDLER_GO_ON;
-+ }
-+
-+ {
-+ unsigned int filesize = sce->st.st_size;
-+
-+ struct atom_t leaf_atom;
-+ while(ftell(infile) < filesize)
-+ {
-+ if(!atom_read_header(infile, &leaf_atom))
-+ break;
-+
-+ atom_print(&leaf_atom);
-+
-+ if(atom_is(&leaf_atom, "ftyp"))
-+ {
-+ ftyp_atom = leaf_atom;
-+ ftyp_data = malloc(ftyp_atom.size_);
-+ fseek(infile, ftyp_atom.start_, SEEK_SET);
-+ fread(ftyp_data, ftyp_atom.size_, 1, infile);
-+ }
-+ else
-+ if(atom_is(&leaf_atom, "moov"))
-+ {
<<Diff was trimmed, longer than 597 lines>>
---- CVS-web:
http://cvs.pld-linux.org/cgi-bin/cvsweb.cgi/SOURCES/lighttpd-mod_h264_streaming.patch?r1=1.1&r2=1.2&f=u
More information about the pld-cvs-commit
mailing list