Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
B
babeld
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Analytics
Analytics
CI / CD
Repository
Value Stream
Wiki
Wiki
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
nexedi
babeld
Commits
86e9e0c4
Commit
86e9e0c4
authored
May 16, 2014
by
Juliusz Chroboczek
Browse files
Options
Browse Files
Download
Plain Diff
Merge branch 'rtt-metric-for-merge'
Conflicts: CHANGES
parents
81934a11
67e54a2b
Changes
13
Expand all
Show whitespace changes
Inline
Side-by-side
Showing
13 changed files
with
432 additions
and
24 deletions
+432
-24
CHANGES
CHANGES
+6
-0
babeld.c
babeld.c
+6
-3
babeld.man
babeld.man
+34
-0
configuration.c
configuration.c
+38
-4
interface.c
interface.c
+22
-0
interface.h
interface.h
+16
-1
local.c
local.c
+11
-2
message.c
message.c
+225
-9
message.h
message.h
+1
-0
neighbour.c
neighbour.c
+41
-3
neighbour.h
neighbour.h
+9
-0
util.c
util.c
+13
-1
util.h
util.h
+10
-1
No files found.
CHANGES
View file @
86e9e0c4
babeld-1.5.0 (unreleased)
* Added support for an RTT-based metric -- see the description of
"enable-timestamps" in the manual page. This work was done by
Baptiste Jonglez with help from Matthieu Boutier.
15 November 2013: babeld-1.4.3
* Added random-id option to config file (equivalent to -r).
...
...
babeld.c
View file @
86e9e0c4
...
...
@@ -148,13 +148,13 @@ main(int argc, char **argv)
goto
usage
;
break
;
case
'h'
:
default_wireless_hello_interval
=
parse_
msec
(
optarg
);
default_wireless_hello_interval
=
parse_
thousands
(
optarg
);
if
(
default_wireless_hello_interval
<=
0
||
default_wireless_hello_interval
>
0xFFFF
*
10
)
goto
usage
;
break
;
case
'H'
:
default_wired_hello_interval
=
parse_
msec
(
optarg
);
default_wired_hello_interval
=
parse_
thousands
(
optarg
);
if
(
default_wired_hello_interval
<=
0
||
default_wired_hello_interval
>
0xFFFF
*
10
)
goto
usage
;
...
...
@@ -1052,12 +1052,15 @@ dump_tables(FILE *out)
fprintf
(
out
,
"My id %s seqno %d
\n
"
,
format_eui64
(
myid
),
myseqno
);
FOR_ALL_NEIGHBOURS
(
neigh
)
{
fprintf
(
out
,
"Neighbour %s dev %s reach %04x rxcost %d txcost %d chan %d%s.
\n
"
,
fprintf
(
out
,
"Neighbour %s dev %s reach %04x rxcost %d txcost %d "
"rtt %s rttcost %d chan %d%s.
\n
"
,
format_address
(
neigh
->
address
),
neigh
->
ifp
->
name
,
neigh
->
reach
,
neighbour_rxcost
(
neigh
),
neigh
->
txcost
,
format_thousands
(
neigh
->
rtt
),
neighbour_rttcost
(
neigh
),
neigh
->
ifp
->
channel
,
if_up
(
neigh
->
ifp
)
?
""
:
" (down)"
);
}
...
...
babeld.man
View file @
86e9e0c4
...
...
@@ -329,6 +329,40 @@ This defines the interval between full routing table dumps sent on this
interface; since Babel uses triggered updates and doesn't count to
infinity, this can be set to a fairly large value, unless significant
packet loss is expected. The default is four times the hello interval.
.TP
.BR enable\-timestamps " {" true | false }
Enable sending timestamps with each Hello and IHU message in order to
compute RTT values. The default is
.BR false .
.TP
.BI rtt\-exponential\-decay " decay"
This specifies the decay factor for the exponential moving average of
RTT samples, in units of 1/256. Must be between 1 and 256, inclusive.
Higher values discard old samples faster. The default is
.BR 42 .
.TP
.BI rtt\-min " rtt"
This specifies the minimum RTT, in milliseconds, starting from which
we increase the cost to a neighbour. The additional cost is linear in
(rtt -
.BR rtt\-min ).
The default is
.B 10
ms.
.TP
.BI rtt\-max " rtt"
This specifies the maximum RTT, in milliseconds, above which we don't
increase the cost to a neighbour. The default is
.B 120
ms.
.TP
.BI max\-rtt\-penalty " cost"
This specifies the maximum cost added to a neighbour because of RTT,
i.e. when the RTT is higher or equal than
.BR rtt\-max .
The default is
.BR 0 ,
which effectively disables the use of a RTT-based cost.
.SS Filtering rules
A filtering rule is defined by a single line with the following format:
.IP
...
...
configuration.c
View file @
86e9e0c4
...
...
@@ -148,14 +148,14 @@ getint(int c, int *int_r, gnc_t gnc, void *closure)
}
static
int
get
msec
(
int
c
,
int
*
int_r
,
gnc_t
gnc
,
void
*
closure
)
get
thousands
(
int
c
,
int
*
int_r
,
gnc_t
gnc
,
void
*
closure
)
{
char
*
t
;
int
i
;
c
=
getword
(
c
,
&
t
,
gnc
,
closure
);
if
(
c
<
-
1
)
return
c
;
i
=
parse_
msec
(
t
);
i
=
parse_
thousands
(
t
);
if
(
i
<
0
)
{
free
(
t
);
return
-
2
;
...
...
@@ -408,13 +408,13 @@ parse_anonymous_ifconf(int c, gnc_t gnc, void *closure,
if_conf
->
cost
=
cost
;
}
else
if
(
strcmp
(
token
,
"hello-interval"
)
==
0
)
{
int
interval
;
c
=
get
msec
(
c
,
&
interval
,
gnc
,
closure
);
c
=
get
thousands
(
c
,
&
interval
,
gnc
,
closure
);
if
(
c
<
-
1
||
interval
<=
0
||
interval
>
10
*
0xFFFF
)
goto
error
;
if_conf
->
hello_interval
=
interval
;
}
else
if
(
strcmp
(
token
,
"update-interval"
)
==
0
)
{
int
interval
;
c
=
get
msec
(
c
,
&
interval
,
gnc
,
closure
);
c
=
get
thousands
(
c
,
&
interval
,
gnc
,
closure
);
if
(
c
<
-
1
||
interval
<=
0
||
interval
>
10
*
0xFFFF
)
goto
error
;
if_conf
->
update_interval
=
interval
;
...
...
@@ -464,6 +464,36 @@ parse_anonymous_ifconf(int c, gnc_t gnc, void *closure,
if
((
if_conf
->
channel
<
1
||
if_conf
->
channel
>
255
)
&&
if_conf
->
channel
!=
IF_CHANNEL_NONINTERFERING
)
goto
error
;
}
else
if
(
strcmp
(
token
,
"enable-timestamps"
)
==
0
)
{
int
v
;
c
=
getbool
(
c
,
&
v
,
gnc
,
closure
);
if
(
c
<
-
1
)
goto
error
;
if_conf
->
enable_timestamps
=
v
;
}
else
if
(
strcmp
(
token
,
"rtt-exponential-decay"
)
==
0
)
{
int
decay
;
c
=
getint
(
c
,
&
decay
,
gnc
,
closure
);
if
(
c
<
-
1
||
decay
<=
0
||
decay
>
256
)
goto
error
;
if_conf
->
rtt_exponential_decay
=
decay
;
}
else
if
(
strcmp
(
token
,
"rtt-min"
)
==
0
)
{
int
rtt
;
c
=
getthousands
(
c
,
&
rtt
,
gnc
,
closure
);
if
(
c
<
-
1
||
rtt
<=
0
)
goto
error
;
if_conf
->
rtt_min
=
rtt
;
}
else
if
(
strcmp
(
token
,
"rtt-max"
)
==
0
)
{
int
rtt
;
c
=
getthousands
(
c
,
&
rtt
,
gnc
,
closure
);
if
(
c
<
-
1
||
rtt
<=
0
)
goto
error
;
if_conf
->
rtt_max
=
rtt
;
}
else
if
(
strcmp
(
token
,
"max-rtt-penalty"
)
==
0
)
{
int
cost
;
c
=
getint
(
c
,
&
cost
,
gnc
,
closure
);
if
(
c
<
-
1
||
cost
<=
0
||
cost
>
0xFFFF
)
goto
error
;
if_conf
->
max_rtt_penalty
=
cost
;
}
else
{
goto
error
;
}
...
...
@@ -544,6 +574,10 @@ merge_ifconf(struct interface_conf *dest,
MERGE
(
lq
);
MERGE
(
faraway
);
MERGE
(
channel
);
MERGE
(
rtt_exponential_decay
);
MERGE
(
rtt_min
);
MERGE
(
rtt_max
);
MERGE
(
max_rtt_penalty
);
#undef MERGE
}
...
...
interface.c
View file @
86e9e0c4
...
...
@@ -293,6 +293,9 @@ interface_up(struct interface *ifp, int up)
if
(
IF_CONF
(
ifp
,
faraway
)
==
CONFIG_YES
)
ifp
->
flags
|=
IF_FARAWAY
;
if
(
IF_CONF
(
ifp
,
enable_timestamps
)
==
CONFIG_YES
)
ifp
->
enable_timestamps
=
1
;
if
(
IF_CONF
(
ifp
,
hello_interval
)
>
0
)
ifp
->
hello_interval
=
IF_CONF
(
ifp
,
hello_interval
);
else
if
((
ifp
->
flags
&
IF_WIRED
))
...
...
@@ -305,6 +308,25 @@ interface_up(struct interface *ifp, int up)
IF_CONF
(
ifp
,
update_interval
)
:
ifp
->
hello_interval
*
4
;
ifp
->
rtt_exponential_decay
=
IF_CONF
(
ifp
,
rtt_exponential_decay
)
>
0
?
IF_CONF
(
ifp
,
rtt_exponential_decay
)
:
42
;
ifp
->
rtt_min
=
IF_CONF
(
ifp
,
rtt_min
)
>
0
?
IF_CONF
(
ifp
,
rtt_min
)
:
10000
;
ifp
->
rtt_max
=
IF_CONF
(
ifp
,
rtt_max
)
>
0
?
IF_CONF
(
ifp
,
rtt_max
)
:
120000
;
if
(
ifp
->
rtt_max
<=
ifp
->
rtt_min
)
{
fprintf
(
stderr
,
"Uh, rtt-max is less than or equal to rtt-min (%d <= %d). "
"Setting it to %d.
\n
"
,
ifp
->
rtt_max
,
ifp
->
rtt_min
,
ifp
->
rtt_min
+
10000
);
ifp
->
rtt_max
=
ifp
->
rtt_min
+
10000
;
}
ifp
->
max_rtt_penalty
=
IF_CONF
(
ifp
,
max_rtt_penalty
);
if
(
ifp
->
ll
)
free
(
ifp
->
ll
);
ifp
->
numll
=
0
;
...
...
interface.h
View file @
86e9e0c4
...
...
@@ -37,6 +37,11 @@ struct interface_conf {
char
lq
;
char
faraway
;
int
channel
;
int
enable_timestamps
;
unsigned
int
rtt_exponential_decay
;
unsigned
int
rtt_min
;
unsigned
int
rtt_max
;
unsigned
int
max_rtt_penalty
;
struct
interface_conf
*
next
;
};
...
...
@@ -72,7 +77,9 @@ struct interface {
unsigned
char
(
*
ll
)[
16
];
int
buffered
;
int
bufsize
;
char
have_buffered_hello
;
/* Relative position of the Hello message in the send buffer, or
(-1) if there is none. */
int
buffered_hello
;
char
have_buffered_id
;
char
have_buffered_nh
;
char
have_buffered_prefix
;
...
...
@@ -89,6 +96,14 @@ struct interface {
unsigned
short
hello_seqno
;
unsigned
hello_interval
;
unsigned
update_interval
;
int
enable_timestamps
;
/* A higher value means we forget old RTT samples faster. Must be
between 1 and 256, inclusive. */
unsigned
int
rtt_exponential_decay
;
/* Parameters for computing the cost associated to RTT. */
unsigned
int
rtt_min
;
unsigned
int
rtt_max
;
unsigned
int
max_rtt_penalty
;
};
#define IF_CONF(_ifp, _field) \
...
...
local.c
View file @
86e9e0c4
...
...
@@ -133,12 +133,20 @@ local_kind(int kind)
static
void
local_notify_neighbour_1
(
int
s
,
struct
neighbour
*
neigh
,
int
kind
)
{
char
buf
[
512
];
char
buf
[
512
]
,
rttbuf
[
64
]
;
int
rc
;
rttbuf
[
0
]
=
'\0'
;
if
(
valid_rtt
(
neigh
))
{
rc
=
snprintf
(
rttbuf
,
64
,
" rtt %s rttcost %d"
,
format_thousands
(
neigh
->
rtt
),
neighbour_rttcost
(
neigh
));
if
(
rc
<
0
||
rc
>=
64
)
rttbuf
[
0
]
=
'\0'
;
}
rc
=
snprintf
(
buf
,
512
,
"%s neighbour %lx address %s "
"if %s reach %04x rxcost %d txcost %d cost %d
\n
"
,
"if %s reach %04x rxcost %d txcost %d
%s
cost %d
\n
"
,
local_kind
(
kind
),
/* Neighbours never move around in memory , so we can use the
address as a unique identifier. */
...
...
@@ -148,6 +156,7 @@ local_notify_neighbour_1(int s, struct neighbour *neigh, int kind)
neigh
->
reach
,
neighbour_rxcost
(
neigh
),
neighbour_txcost
(
neigh
),
rttbuf
,
neighbour_cost
(
neigh
));
if
(
rc
<
0
||
rc
>=
512
)
...
...
message.c
View file @
86e9e0c4
This diff is collapsed.
Click to expand it.
message.h
View file @
86e9e0c4
...
...
@@ -44,6 +44,7 @@ THE SOFTWARE.
#define SUBTLV_PAD1 0
#define SUBTLV_PADN 1
#define SUBTLV_DIVERSITY 2
/* Also known as babelz. */
#define SUBTLV_TIMESTAMP 3
/* Used to compute RTT. */
extern
unsigned
short
myseqno
;
extern
struct
timeval
seqno_time
;
...
...
neighbour.c
View file @
86e9e0c4
...
...
@@ -25,6 +25,7 @@ THE SOFTWARE.
#include <stdio.h>
#include <sys/time.h>
#include <time.h>
#include <assert.h>
#include "babeld.h"
#include "util.h"
...
...
@@ -97,6 +98,10 @@ find_neighbour(const unsigned char *address, struct interface *ifp)
neigh
->
hello_time
=
zero
;
neigh
->
hello_interval
=
0
;
neigh
->
ihu_interval
=
0
;
neigh
->
hello_send_us
=
0
;
neigh
->
hello_rtt_receive_time
=
zero
;
neigh
->
rtt
=
0
;
neigh
->
rtt_time
=
zero
;
neigh
->
ifp
=
ifp
;
neigh
->
next
=
neighs
;
neighs
=
neigh
;
...
...
@@ -293,10 +298,33 @@ neighbour_rxcost(struct neighbour *neigh)
}
}
unsigned
neighbour_rttcost
(
struct
neighbour
*
neigh
)
{
struct
interface
*
ifp
=
neigh
->
ifp
;
if
(
!
ifp
->
max_rtt_penalty
||
!
valid_rtt
(
neigh
))
return
0
;
/* Function: linear behaviour between rtt_min and rtt_max. */
if
(
neigh
->
rtt
<=
ifp
->
rtt_min
)
{
return
0
;
}
else
if
(
neigh
->
rtt
<=
ifp
->
rtt_max
)
{
unsigned
long
long
tmp
=
(
unsigned
long
long
)
ifp
->
max_rtt_penalty
*
(
neigh
->
rtt
-
ifp
->
rtt_min
)
/
(
ifp
->
rtt_max
-
ifp
->
rtt_min
);
assert
((
tmp
&
0x7FFFFFFF
)
==
tmp
);
return
tmp
;
}
else
{
return
ifp
->
max_rtt_penalty
;
}
}
unsigned
neighbour_cost
(
struct
neighbour
*
neigh
)
{
unsigned
a
,
b
;
unsigned
a
,
b
,
cost
;
if
(
!
if_up
(
neigh
->
ifp
))
return
INFINITY
;
...
...
@@ -311,7 +339,7 @@ neighbour_cost(struct neighbour *neigh)
return
INFINITY
;
if
(
!
(
neigh
->
ifp
->
flags
&
IF_LQ
)
||
(
a
<
256
&&
b
<
256
))
{
return
a
;
cost
=
a
;
}
else
{
/* a = 256/alpha, b = 256/beta, where alpha and beta are the expected
probabilities of a packet getting through in the direct and reverse
...
...
@@ -320,6 +348,16 @@ neighbour_cost(struct neighbour *neigh)
b
=
MAX
(
b
,
256
);
/* 1/(alpha * beta), which is just plain ETX. */
/* Since a and b are capped to 16 bits, overflow is impossible. */
return
MIN
((
a
*
b
+
128
)
>>
8
,
INFINITY
)
;
cost
=
(
a
*
b
+
128
)
>>
8
;
}
cost
+=
neighbour_rttcost
(
neigh
);
return
MIN
(
cost
,
INFINITY
);
}
int
valid_rtt
(
struct
neighbour
*
neigh
)
{
return
(
timeval_minus_msec
(
&
now
,
&
neigh
->
rtt_time
)
<
180000
)
?
1
:
0
;
}
neighbour.h
View file @
86e9e0c4
...
...
@@ -31,6 +31,13 @@ struct neighbour {
struct
timeval
ihu_time
;
unsigned
short
hello_interval
;
/* in centiseconds */
unsigned
short
ihu_interval
;
/* in centiseconds */
/* Used for RTT estimation. */
/* Absolute time (modulo 2^32) at which the Hello was sent,
according to remote clock. */
unsigned
int
hello_send_us
;
struct
timeval
hello_rtt_receive_time
;
unsigned
int
rtt
;
struct
timeval
rtt_time
;
struct
interface
*
ifp
;
};
...
...
@@ -47,4 +54,6 @@ int update_neighbour(struct neighbour *neigh, int hello, int hello_interval);
unsigned
check_neighbours
(
void
);
unsigned
neighbour_txcost
(
struct
neighbour
*
neigh
);
unsigned
neighbour_rxcost
(
struct
neighbour
*
neigh
);
unsigned
neighbour_rttcost
(
struct
neighbour
*
neigh
);
unsigned
neighbour_cost
(
struct
neighbour
*
neigh
);
int
valid_rtt
(
struct
neighbour
*
neigh
);
util.c
View file @
86e9e0c4
...
...
@@ -152,8 +152,10 @@ parse_nat(const char *string)
return
(
int
)
l
;
}
/* Given a fixed-point string such as "42.1337", returns 1000 times
the value of the string, here 42133. */
int
parse_
msec
(
const
char
*
string
)
parse_
thousands
(
const
char
*
string
)
{
unsigned
int
in
,
fl
;
int
i
,
j
;
...
...
@@ -293,6 +295,16 @@ format_eui64(const unsigned char *eui)
return
buf
[
i
];
}
const
char
*
format_thousands
(
unsigned
int
value
)
{
static
char
buf
[
4
][
15
];
static
int
i
=
0
;
i
=
(
i
+
1
)
%
4
;
snprintf
(
buf
[
i
],
15
,
"%d.%.3d"
,
value
/
1000
,
value
%
1000
);
return
buf
[
i
];
}
int
parse_address
(
const
char
*
address
,
unsigned
char
*
addr_r
,
int
*
af_r
)
{
...
...
util.h
View file @
86e9e0c4
...
...
@@ -66,6 +66,14 @@ seqno_plus(unsigned short s, int plus)
return
((
s
+
plus
)
&
0xFFFF
);
}
/* Returns a time in microseconds on 32 bits (thus modulo 2^32,
i.e. about 4295 seconds). */
static
inline
unsigned
int
time_us
(
const
struct
timeval
t
)
{
return
(
unsigned
int
)
(
t
.
tv_sec
*
1000000
+
t
.
tv_usec
);
}
int
roughly
(
int
value
);
void
timeval_minus
(
struct
timeval
*
d
,
const
struct
timeval
*
s1
,
const
struct
timeval
*
s2
);
...
...
@@ -78,7 +86,7 @@ int timeval_compare(const struct timeval *s1, const struct timeval *s2)
void
timeval_min
(
struct
timeval
*
d
,
const
struct
timeval
*
s
);
void
timeval_min_sec
(
struct
timeval
*
d
,
time_t
secs
);
int
parse_nat
(
const
char
*
string
)
ATTRIBUTE
((
pure
));
int
parse_
msec
(
const
char
*
string
)
ATTRIBUTE
((
pure
));
int
parse_
thousands
(
const
char
*
string
)
ATTRIBUTE
((
pure
));
void
do_debugf
(
int
level
,
const
char
*
format
,
...)
ATTRIBUTE
((
format
(
printf
,
2
,
3
)))
COLD
;
int
in_prefix
(
const
unsigned
char
*
restrict
address
,
...
...
@@ -90,6 +98,7 @@ unsigned char *mask_prefix(unsigned char *restrict ret,
const
char
*
format_address
(
const
unsigned
char
*
address
);
const
char
*
format_prefix
(
const
unsigned
char
*
address
,
unsigned
char
prefix
);
const
char
*
format_eui64
(
const
unsigned
char
*
eui
);
const
char
*
format_thousands
(
unsigned
int
value
);
int
parse_address
(
const
char
*
address
,
unsigned
char
*
addr_r
,
int
*
af_r
);
int
parse_net
(
const
char
*
net
,
unsigned
char
*
prefix_r
,
unsigned
char
*
plen_r
,
int
*
af_r
);
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment