Skip to content
Snippets Groups Projects
Commit 9a3250d8 authored by Julian Rother's avatar Julian Rother
Browse files

Added probe worker

parent cb71f573
Branches
No related tags found
No related merge requests found
probe.c 0 → 100644
#include <libavcodec/avcodec.h>
#include <libavformat/avformat.h>
#include <libxml/tree.h>
#include <libxml/parser.h>
#include <libxml/xpath.h>
#include <libxml/xpathInternals.h>
#include "util.h"
#include "config.h"
static char *getxmlattr(xmlAttr *a, char *name, char *err)
{
for (; a && strcmp(a->name, name); a = a->next);
if (!a)
return err;
return a->children->content;
}
char *get_xmpchapters(char *xmp)
{
int i, len, maxlen;
char *out;
xmlDocPtr doc;
xmlXPathContextPtr xpath;
xmlXPathObjectPtr res;
xmlNodePtr node;
double framerate, start;
if (!(doc = xmlParseMemory(xmp, strlen(xmp))))
return "";
if (!(xpath = xmlXPathNewContext(doc)))
return "";
xmlXPathRegisterNs(xpath, "x", "adobe:ns:meta/");
xmlXPathRegisterNs(xpath, "rdf", "http://www.w3.org/1999/02/22-rdf-syntax-ns#");
xmlXPathRegisterNs(xpath, "xmpDM", "http://ns.adobe.com/xmp/1.0/DynamicMedia/");
res = xmlXPathEvalExpression("/x:xmpmeta/rdf:RDF/rdf:Description/@xmpDM:videoFrameRate", xpath);
if (!res || !res->nodesetval->nodeNr)
return "";
framerate = strtod(res->nodesetval->nodeTab[0]->children->content, 0);
xmlXPathFreeObject(res);
res = xmlXPathEvalExpression("/x:xmpmeta/rdf:RDF/rdf:Description/xmpDM:Tracks/rdf:Bag/rdf:li/rdf:Description/xmpDM:markers/rdf:Seq/rdf:li/rdf:Description", xpath);
if (!res || !res->nodesetval)
return "";
len = 0; maxlen = res->nodesetval->nodeNr*200;
out = malloc(maxlen);
len += xsnprintf(out+len, maxlen-len-1, "[");
for (i = 0; i < res->nodesetval->nodeNr; i ++)
{
start = atoi(getxmlattr(res->nodesetval->nodeTab[i]->properties, "startTime", "0"))/framerate;
if (i)
len += xsnprintf(out+len, maxlen-len-1, ",");
len += xsnprintf(out+len, maxlen-len-1, "{\"time\": %f, \"text\": \"%s\"}",
start, jescape(getxmlattr(res->nodesetval->nodeTab[i]->properties, "name", "")));
}
len += xsnprintf(out+len, maxlen-len-1, "]");
return out;
}
int main(int argc, char *argv[])
{
int jobid;
char path[100], *xmp;
AVFormatContext *demux, *mux;
AVDictionaryEntry *tag;
AVDictionary *opts;
if (argc != 5)
return 1;
av_register_all();
av_log_set_callback(avlogbuf_callback);
jobid = atoi(argv[1]);
xsnprintf(BL(path), "%s/%s", CONFIG_VIDEOS_RAW,
jstr(jlookup(argv[4], "path"), ""));
ping_job(jobid, "running", 0);
opts = 0;
av_dict_set_int(&opts, "export_xmp", 1, 0);
demux = 0;
if (avformat_open_input(&demux, path, 0, &opts))
goto fail;
avformat_find_stream_info(demux, 0);
if (tag = av_dict_get(demux->metadata, "xmp", 0, 0))
ping_job(jobid, "finished", "{\"xmp_chapters\": %s, \"duration\": %f, \"log\": \"%s\"}", get_xmpchapters(tag->value), demux->duration*av_q2d(AV_TIME_BASE_Q), get_avlogbuf());
else
ping_job(jobid, "finished", "{\"duration\": %f, \"log\": \"%s\"}", demux->duration*av_q2d(AV_TIME_BASE_Q), get_avlogbuf());
return 0;
fail:
ping_job(jobid, "failed", "{\"log\": \"%s\"}", get_avlogbuf());
return 1;
}
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment