Browse Source

support some flags passed from rtpproxy-ng module

git.mgm/mediaproxy-ng/2.2
Richard Fuchs 13 years ago
parent
commit
5d1c2aabed
6 changed files with 110 additions and 26 deletions
  1. +15
    -0
      daemon/bencode.h
  2. +59
    -15
      daemon/call.c
  3. +10
    -5
      daemon/call.h
  4. +9
    -3
      daemon/sdp.c
  5. +11
    -1
      daemon/sdp.h
  6. +6
    -2
      daemon/str.h

+ 15
- 0
daemon/bencode.h View File

@ -122,6 +122,10 @@ bencode_item_t *bencode_string_len(bencode_buffer_t *buf, const char *s, int len
* to bencode_string_len(). */
static inline bencode_item_t *bencode_string(bencode_buffer_t *buf, const char *s);
/* Convenience function to compare a string object to a regular C string. Returns 2 if object
* isn't a string object, otherwise returns according to strcmp(). */
static inline int bencode_strcmp(bencode_item_t *a, const char *b);
/* Creates a new byte-string object from a "str" object. The string does not have to be null-
* terminated. */
static inline bencode_item_t *bencode_str(bencode_buffer_t *buf, const str *s);
@ -360,5 +364,16 @@ static inline str *bencode_collapse_str(bencode_item_t *root, str *out) {
out->s = bencode_collapse(root, &out->len);
return out;
}
static inline int bencode_strcmp(bencode_item_t *a, const char *b) {
int len;
if (a->type != BENCODE_STRING)
return 2;
len = strlen(b);
if (a->iov[1].iov_len < len)
return -1;
if (a->iov[1].iov_len > len)
return 1;
return memcmp(a->iov[1].iov_base, b, len);
}
#endif

+ 59
- 15
daemon/call.c View File

@ -45,10 +45,6 @@ static __thread const str *log_info;
/* also serves as array index for callstream->peers[] */
enum opmode {
OP_OFFER = 0,
OP_ANSWER = 1,
};
struct iterator_helper {
GSList *del;
struct streamrelay *ports[0x10000];
@ -1174,7 +1170,7 @@ static void callstream_free(void *ptr) {
}
/* called with call->lock held */
static int call_streams(struct call *c, GQueue *s, const str *tag, enum opmode opmode) {
static int call_streams(struct call *c, GQueue *s, const str *tag, enum call_opmode opmode) {
GQueue *q;
GList *i, *l;
struct stream_input *t;
@ -1220,7 +1216,7 @@ static int call_streams(struct call *c, GQueue *s, const str *tag, enum opmode o
found:
/* cs_o remains locked if set */
if (!opmode) { /* request */
if (opmode == OP_OFFER) {
DBG("creating new callstream");
cs = callstream_new(c, t->stream.num);
@ -1507,18 +1503,18 @@ int call_stream_address(GString *o, struct peer *p, enum stream_address_format f
static str *streams_print(GQueue *s, int rawnum, enum opmode opmode, const char *prefix, enum stream_address_format format) {
static str *streams_print(GQueue *s, int num, enum call_opmode opmode, const char *prefix, enum stream_address_format format) {
GString *o;
int i, num, off;
int i, off;
GList *l;
struct callstream *t;
struct streamrelay *x;
int af;
num = abs(rawnum);
off = opmode; /* 0 or 1 */
if (num < 0)
off ^= 1; /* 1 or 0 */
num = abs(num);
o = g_string_new_str();
if (prefix)
@ -1635,7 +1631,7 @@ static struct call *call_get(const str *callid, const str *viabranch, struct cal
}
/* returns call with lock held, or possibly NULL iff opmode == OP_ANSWER */
static struct call *call_get_opmode(const str *callid, const str *viabranch, struct callmaster *m, enum opmode opmode) {
static struct call *call_get_opmode(const str *callid, const str *viabranch, struct callmaster *m, enum call_opmode opmode) {
if (opmode == OP_OFFER)
return call_get_or_create(callid, viabranch, m);
return call_get(callid, viabranch, m);
@ -1686,7 +1682,7 @@ fail:
return -1;
}
static str *call_update_lookup_udp(char **out, struct callmaster *m, enum opmode opmode, int tagidx) {
static str *call_update_lookup_udp(char **out, struct callmaster *m, enum call_opmode opmode, int tagidx) {
struct call *c;
GQueue q = G_QUEUE_INIT;
struct stream_input st;
@ -1738,7 +1734,7 @@ str *call_lookup_udp(char **out, struct callmaster *m) {
return call_update_lookup_udp(out, m, OP_ANSWER, RE_UDP_UL_TOTAG);
}
static str *call_request_lookup(char **out, struct callmaster *m, enum opmode opmode, const char *tagstr) {
static str *call_request_lookup(char **out, struct callmaster *m, enum call_opmode opmode, const char *tagstr) {
struct call *c;
GQueue s = G_QUEUE_INIT;
int num;
@ -2091,6 +2087,53 @@ struct callstream *callstream_new(struct call *ca, int num) {
}
static void call_ng_process_flags(struct sdp_ng_flags *out, GQueue *streams, bencode_item_t *input) {
bencode_item_t *list, *it;
struct stream_input *si;
int diridx;
enum stream_direction dirs[2];
GList *gl;
ZERO(*out);
ZERO(dirs);
if ((list = bencode_dictionary_get_expect(input, "flags", BENCODE_LIST))) {
for (it = list->child; it; it = it->sibling) {
if (!bencode_strcmp(it, "trust-address")) /* XXX not implemented */
out->trust_address = 1;
else if (!bencode_strcmp(it, "symmetric"))
out->symmetric = 1;
else if (!bencode_strcmp(it, "asymmetric"))
out->asymmetric = 1;
}
}
if ((list = bencode_dictionary_get_expect(input, "replace", BENCODE_LIST))) {
for (it = list->child; it; it = it->sibling) {
if (!bencode_strcmp(it, "origin"))
out->replace_origin = 1;
else if (!bencode_strcmp(it, "session-connection"))
out->replace_sess_conn = 1;
}
}
diridx = 0;
if ((list = bencode_dictionary_get_expect(input, "direction", BENCODE_LIST))) {
for (it = list->child; it && diridx < 2; it = it->sibling) {
if (!bencode_strcmp(it, "internal"))
dirs[diridx++] = DIR_INTERNAL;
else if (!bencode_strcmp(it, "external"))
dirs[diridx++] = DIR_INTERNAL;
}
for (gl = streams->head; gl; gl = gl->next) {
si = gl->data;
si->direction[0] = dirs[0];
si->direction[1] = dirs[1];
}
}
}
const char *call_offer(bencode_item_t *input, struct callmaster *m, bencode_item_t *output) {
str sdp, fromtag, viabranch, callid, *sdp_new;
char *errstr;
@ -2098,6 +2141,7 @@ const char *call_offer(bencode_item_t *input, struct callmaster *m, bencode_item
GQueue streams = G_QUEUE_INIT;
struct call *call;
int num;
struct sdp_ng_flags flags;
if (!bencode_dictionary_get_str(input, "sdp", &sdp))
return "No SDP body in message";
@ -2108,8 +2152,6 @@ const char *call_offer(bencode_item_t *input, struct callmaster *m, bencode_item
bencode_dictionary_get_str(input, "via-branch", &viabranch);
log_info = &viabranch;
/* XXX get rid of "direction" and use "desired_family" as intended? */
if (sdp_parse(&sdp, &parsed))
return "Failed to parse SDP";
@ -2117,11 +2159,13 @@ const char *call_offer(bencode_item_t *input, struct callmaster *m, bencode_item
if (sdp_streams(&parsed, &streams))
goto out;
call_ng_process_flags(&flags, &streams, input);
call = call_get_or_create(&callid, &viabranch, m);
log_info = &viabranch;
num = call_streams(call, &streams, &fromtag, OP_OFFER);
sdp_new = sdp_replace(&sdp, &parsed, call, abs(num), (num >= 0) ? 0 : 1);
sdp_new = sdp_replace(&sdp, &parsed, call, num, OP_OFFER, &flags);
mutex_unlock(&call->lock);
obj_put(call);


+ 10
- 5
daemon/call.h View File

@ -35,6 +35,15 @@ enum stream_address_format {
SAF_UDP,
SAF_NG,
};
enum stream_direction {
DIR_UNKNOWN = 0,
DIR_INTERNAL,
DIR_EXTERNAL,
};
enum call_opmode {
OP_OFFER = 0,
OP_ANSWER = 1,
};
struct stats {
u_int64_t packets;
@ -49,11 +58,7 @@ struct stream {
};
struct stream_input {
struct stream stream;
enum {
DIR_UNKNOWN = 0,
DIR_INTERNAL,
DIR_EXTERNAL,
} direction[2];
enum stream_direction direction[2];
};
struct streamrelay {
int fd;


+ 9
- 3
daemon/sdp.c View File

@ -452,11 +452,17 @@ static void chopper_destroy(struct string_chopper *chop) {
/* XXX use port numbers as index */
/* XXX get rid of num/off parameters? */
/* XXX use iovec based rewriting */
str *sdp_replace(str *body, GQueue *sessions, struct call *call, int num, int off) {
str *sdp_replace(str *body, GQueue *sessions, struct call *call, int num, enum call_opmode opmode, struct sdp_ng_flags *flags) {
struct sdp_session *session;
struct sdp_media *media;
GList *l, *k, *m;
struct string_chopper chop;
int off;
off = opmode;
if (num < 0)
off ^= 1;
num = abs(num);
chopper_init(&chop, body);
m = call->callstreams->head;
@ -464,7 +470,7 @@ str *sdp_replace(str *body, GQueue *sessions, struct call *call, int num, int of
for (l = sessions->head; l; l = l->next) {
session = l->data;
if (session->origin.parsed) {
if (session->origin.parsed && flags->replace_origin) {
if (replace_network_address(&chop, &session->origin.address, m, off))
goto error;
}
@ -480,7 +486,7 @@ str *sdp_replace(str *body, GQueue *sessions, struct call *call, int num, int of
if (replace_port(&chop, &media->port, m, off))
goto error;
if (media->connection.parsed) {
if (media->connection.parsed && flags->replace_sess_conn) {
if (replace_network_address(&chop, &media->connection.address, m, off))
goto error;
}


+ 11
- 1
daemon/sdp.h View File

@ -5,9 +5,19 @@
#include "str.h"
#include "call.h"
struct sdp_ng_flags {
int desired_family[2];
int asymmetric:1,
symmetric:1,
trust_address:1,
replace_origin:1,
replace_sess_conn:1;
};
int sdp_parse(str *body, GQueue *sessions);
int sdp_streams(const GQueue *sessions, GQueue *streams);
void sdp_free(GQueue *sessions);
str *sdp_replace(str *body, GQueue *sessions, struct call *call, int num, int off);
str *sdp_replace(str *body, GQueue *sessions, struct call *call, int num, enum call_opmode, struct sdp_ng_flags *);
#endif

+ 6
- 2
daemon/str.h View File

@ -35,6 +35,8 @@ static inline char *str_chr(const str *s, int c);
static inline str *str_chr_str(str *out, const str *s, int c);
/* compares a str to a regular string */
static inline int str_cmp(const str *a, const char *b);
/* compares a str to a non-null-terminated string */
static inline int str_cmp_len(const str *a, const char *b, int len);
/* compares two str objects */
static inline int str_cmp_str(const str *a, const str *b);
/* compares two str objects, allows either to be NULL */
@ -80,8 +82,7 @@ static inline str *str_chr_str(str *out, const str *s, int c) {
out->len = out->s ? (s->len - (out->s - s->s)) : 0;
return out;
}
static inline int str_cmp(const str *a, const char *b) {
int l = strlen(b);
static inline int str_cmp_len(const str *a, const char *b, int l) {
if (a->len < l)
return -1;
if (a->len > l)
@ -90,6 +91,9 @@ static inline int str_cmp(const str *a, const char *b) {
return 0;
return memcmp(a->s, b, l);
}
static inline int str_cmp(const str *a, const char *b) {
return str_cmp_len(a, b, strlen(b));
}
static inline int str_cmp_str(const str *a, const str *b) {
if (a->len < b->len)
return -1;


Loading…
Cancel
Save