00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021 #include <stdio.h>
00022 #include "libavutil/avstring.h"
00023 #include "libavutil/md5.h"
00024 #include "libavutil/mem.h"
00025 #include "libavutil/error.h"
00026 #include "avformat.h"
00027 #include "avio.h"
00028
00029 #define PRIV_SIZE 128
00030
00031 static int md5_open(URLContext *h, const char *filename, int flags)
00032 {
00033 if (PRIV_SIZE < av_md5_size) {
00034 av_log(NULL, AV_LOG_ERROR, "Insuffient size for MD5 context\n");
00035 return -1;
00036 }
00037
00038 if (flags != URL_WRONLY)
00039 return AVERROR(EINVAL);
00040
00041 av_md5_init(h->priv_data);
00042
00043 return 0;
00044 }
00045
00046 static int md5_write(URLContext *h, const unsigned char *buf, int size)
00047 {
00048 av_md5_update(h->priv_data, buf, size);
00049 return size;
00050 }
00051
00052 static int md5_close(URLContext *h)
00053 {
00054 const char *filename = h->filename;
00055 uint8_t md5[16], buf[64];
00056 URLContext *out;
00057 int i, err = 0;
00058
00059 av_md5_final(h->priv_data, md5);
00060 for (i = 0; i < sizeof(md5); i++)
00061 snprintf(buf + i*2, 3, "%02x", md5[i]);
00062 buf[i*2] = '\n';
00063
00064 av_strstart(filename, "md5:", &filename);
00065
00066 if (*filename) {
00067 err = url_open(&out, filename, URL_WRONLY);
00068 if (err)
00069 return err;
00070 err = url_write(out, buf, i*2+1);
00071 url_close(out);
00072 } else {
00073 if (fwrite(buf, 1, i*2+1, stdout) < i*2+1)
00074 err = AVERROR(errno);
00075 }
00076
00077 return err;
00078 }
00079
00080 static int md5_get_handle(URLContext *h)
00081 {
00082 return (intptr_t)h->priv_data;
00083 }
00084
00085 URLProtocol ff_md5_protocol = {
00086 .name = "md5",
00087 .url_open = md5_open,
00088 .url_write = md5_write,
00089 .url_close = md5_close,
00090 .url_get_file_handle = md5_get_handle,
00091 .priv_data_size = PRIV_SIZE,
00092 };