diff --git a/doc/cdeftutorial.1 b/doc/cdeftutorial.1
index 0da42ffca59d55f1b8a8f65e7483b3202135b815..3af03a43e372263a0e5c54411b0f22ed693032c7 100644 (file)
--- a/doc/cdeftutorial.1
+++ b/doc/cdeftutorial.1
-.\" Automatically generated by Pod::Man v1.37, Pod::Parser v1.32
+.\" Automatically generated by Pod::Man 2.1801 (Pod::Simple 3.05)
.\"
.\" Standard preamble:
.\" ========================================================================
.\"
.\" Standard preamble:
.\" ========================================================================
-.de Sh \" Subsection heading
-.br
-.if t .Sp
-.ne 5
-.PP
-\fB\\$1\fR
-.PP
-..
.de Sp \" Vertical space (when we can't use .PP)
.if t .sp .5v
.if n .sp
.de Sp \" Vertical space (when we can't use .PP)
.if t .sp .5v
.if n .sp
. ds R" ''
'br\}
.\"
. ds R" ''
'br\}
.\"
+.\" Escape single quotes in literal strings from groff's Unicode transform.
+.ie \n(.g .ds Aq \(aq
+.el .ds Aq '
+.\"
.\" If the F register is turned on, we'll generate index entries on stderr for
.\" If the F register is turned on, we'll generate index entries on stderr for
-.\" titles (.TH), headers (.SH), subsections (.Sh), items (.Ip), and index
+.\" titles (.TH), headers (.SH), subsections (.SS), items (.Ip), and index
.\" entries marked with X<> in POD. Of course, you'll have to process the
.\" output yourself in some meaningful fashion.
.\" entries marked with X<> in POD. Of course, you'll have to process the
.\" output yourself in some meaningful fashion.
-.if \nF \{\
+.ie \nF \{\
. de IX
. tm Index:\\$1\t\\n%\t"\\$2"
..
. nr % 0
. rr F
.\}
. de IX
. tm Index:\\$1\t\\n%\t"\\$2"
..
. nr % 0
. rr F
.\}
-.\"
-.\" For nroff, turn off justification. Always turn off hyphenation; it makes
-.\" way too many mistakes in technical documents.
-.hy 0
-.if n .na
+.el \{\
+. de IX
+..
+.\}
.\"
.\" Accent mark definitions (@(#)ms.acc 1.5 88/02/08 SMI; from UCB 4.2).
.\" Fear. Run. Save yourself. No user-serviceable parts.
.\"
.\" Accent mark definitions (@(#)ms.acc 1.5 88/02/08 SMI; from UCB 4.2).
.\" Fear. Run. Save yourself. No user-serviceable parts.
.\" ========================================================================
.\"
.IX Title "CDEFTUTORIAL 1"
.\" ========================================================================
.\"
.IX Title "CDEFTUTORIAL 1"
-.TH CDEFTUTORIAL 1 "2008-03-15" "1.3.1" "rrdtool"
+.TH CDEFTUTORIAL 1 "2009-02-21" "1.4.2" "rrdtool"
+.\" For nroff, turn off justification. Always turn off hyphenation; it makes
+.\" way too many mistakes in technical documents.
+.if n .ad l
+.nh
.SH "NAME"
cdeftutorial \- Alex van den Bogaerdt's CDEF tutorial
.SH "DESCRIPTION"
.SH "NAME"
cdeftutorial \- Alex van den Bogaerdt's CDEF tutorial
.SH "DESCRIPTION"
to add it. I will then try to provide an answer in the next release
of this tutorial. No feedback equals no changes! Additions to
this document are also welcome. \*(-- Alex van den Bogaerdt
to add it. I will then try to provide an answer in the next release
of this tutorial. No feedback equals no changes! Additions to
this document are also welcome. \*(-- Alex van den Bogaerdt
-<alex@ergens.op.het.net>
-.Sh "Why this tutorial?"
+<alex@vandenbogaerdt.nl>
+.SS "Why this tutorial?"
.IX Subsection "Why this tutorial?"
One of the powerful parts of RRDtool is its ability to do all sorts
of calculations on the data retrieved from its databases. However,
.IX Subsection "Why this tutorial?"
One of the powerful parts of RRDtool is its ability to do all sorts
of calculations on the data retrieved from its databases. However,
document too simple or even boring. If you do choose to read this
tutorial, I also expect you to have read and fully understand my
other tutorial.
document too simple or even boring. If you do choose to read this
tutorial, I also expect you to have read and fully understand my
other tutorial.
-.Sh "More reading"
+.SS "More reading"
.IX Subsection "More reading"
If you have difficulties with the way I try to explain it please read
Steve Rader's rpntutorial. It may help you understand how this all works.
.IX Subsection "More reading"
If you have difficulties with the way I try to explain it please read
Steve Rader's rpntutorial. It may help you understand how this all works.
.IX Header "RPN-expressions"
\&\s-1RPN\s0 is short-hand for Reverse Polish Notation. It works as follows.
You put the variables or numbers on a stack. You also put operations
.IX Header "RPN-expressions"
\&\s-1RPN\s0 is short-hand for Reverse Polish Notation. It works as follows.
You put the variables or numbers on a stack. You also put operations
-(things\-to\-do) on the stack and this stack is then processed. The result
+(things-to-do) on the stack and this stack is then processed. The result
will be placed on the stack. At the end, there should be exactly one
number left: the outcome of the series of operations. If there is not
exactly one number left, RRDtool will complain loudly.
will be placed on the stack. At the end, there should be exactly one
number left: the outcome of the series of operations. If there is not
exactly one number left, RRDtool will complain loudly.
rewrite the \s-1RPN\s0 into \f(CW\*(C`CDEF:result=a,b,c,d,e,+,+,+,+\*(C'\fR which is
evaluated differently:
.PP
rewrite the \s-1RPN\s0 into \f(CW\*(C`CDEF:result=a,b,c,d,e,+,+,+,+\*(C'\fR which is
evaluated differently:
.PP
-.Vb 13
+.Vb 10
\& push value of variable a on the stack: a
\& push value of variable b on the stack: a b
\& push value of variable c on the stack: a b c
\& push value of variable a on the stack: a
\& push value of variable b on the stack: a b
\& push value of variable c on the stack: a b c
solve most, if not all, problems you encounter.
.SH "Some special numbers"
.IX Header "Some special numbers"
solve most, if not all, problems you encounter.
.SH "Some special numbers"
.IX Header "Some special numbers"
-.Sh "The unknown value"
+.SS "The unknown value"
.IX Subsection "The unknown value"
Sometimes collecting your data will fail. This can be very common,
especially when querying over busy links. RRDtool can be configured
.IX Subsection "The unknown value"
Sometimes collecting your data will fail. This can be very common,
especially when querying over busy links. RRDtool can be configured
.PP
.Vb 7
\& counter value resulting rate
.PP
.Vb 7
\& counter value resulting rate
-\& 10\(aq000
-\& 10\(aq060 1; (10\(aq060\-10\(aq000)/60 == 1
-\& 10\(aq120 1; (10\(aq120\-10\(aq060)/60 == 1
-\& unknown unknown; you don\(aqt know the last value
-\& 10\(aq240 unknown; you don\(aqt know the previous value
-\& 10\(aq300 1; (10\(aq300\-10\(aq240)/60 == 1
+\& 10\*(Aq000
+\& 10\*(Aq060 1; (10\*(Aq060\-10\*(Aq000)/60 == 1
+\& 10\*(Aq120 1; (10\*(Aq120\-10\*(Aq060)/60 == 1
+\& unknown unknown; you don\*(Aqt know the last value
+\& 10\*(Aq240 unknown; you don\*(Aqt know the previous value
+\& 10\*(Aq300 1; (10\*(Aq300\-10\*(Aq240)/60 == 1
.Ve
.PP
If the \s-1CDP\s0 was to be calculated from the last five updates, it would get
.Ve
.PP
If the \s-1CDP\s0 was to be calculated from the last five updates, it would get
You have to decide the proper values for heartbeat, number of PDPs per
\&\s-1CDP\s0 and the xff factor. As you can see from the previous text they define
the behavior of your \s-1RRA\s0.
You have to decide the proper values for heartbeat, number of PDPs per
\&\s-1CDP\s0 and the xff factor. As you can see from the previous text they define
the behavior of your \s-1RRA\s0.
-.Sh "Working with unknown data in your database"
+.SS "Working with unknown data in your database"
.IX Subsection "Working with unknown data in your database"
As you have read in the previous chapter, entries in an \s-1RRA\s0 can be
set to the unknown value. If you do calculations with this type of
.IX Subsection "Working with unknown data in your database"
As you have read in the previous chapter, entries in an \s-1RRA\s0 can be
set to the unknown value. If you do calculations with this type of
had to be zero (because of the same reason: it was not installed).
.PP
There are some examples below that make this change.
had to be zero (because of the same reason: it was not installed).
.PP
There are some examples below that make this change.
-.Sh "Infinity"
+.SS "Infinity"
.IX Subsection "Infinity"
Infinite data is another form of a special number. It cannot be
graphed because by definition you would never reach the infinite
.IX Subsection "Infinity"
Infinite data is another form of a special number. It cannot be
graphed because by definition you would never reach the infinite
infinite height and displaying only the part that is visible in the
current graph. This is probably a good way to approximate infinity
and it sure allows for some neat tricks. See below for examples.
infinite height and displaying only the part that is visible in the
current graph. This is probably a good way to approximate infinity
and it sure allows for some neat tricks. See below for examples.
-.Sh "Working with unknown data and infinity"
+.SS "Working with unknown data and infinity"
.IX Subsection "Working with unknown data and infinity"
Sometimes you would like to discard unknown data and pretend it is zero
(or any other value for that matter) and sometimes you would like to
.IX Subsection "Working with unknown data and infinity"
Sometimes you would like to discard unknown data and pretend it is zero
(or any other value for that matter) and sometimes you would like to
available that show unknown data by using infinity.
.SH "Some examples"
.IX Header "Some examples"
available that show unknown data by using infinity.
.SH "Some examples"
.IX Header "Some examples"
-.Sh "Example: using a recently created \s-1RRD\s0"
+.SS "Example: using a recently created \s-1RRD\s0"
.IX Subsection "Example: using a recently created RRD"
You are keeping statistics on your router for over a year now. Recently
you installed an extra router and you would like to show the combined
.IX Subsection "Example: using a recently created RRD"
You are keeping statistics on your router for over a year now. Recently
you installed an extra router and you would like to show the combined
\& CDEF:result=value,UN,0,value,IF (value,UN) is not true so it becomes 0
\& CDEF:result=0,0,value,IF "IF" will return the 3rd value
\& CDEF:result=value The known value is returned
\& CDEF:result=value,UN,0,value,IF (value,UN) is not true so it becomes 0
\& CDEF:result=0,0,value,IF "IF" will return the 3rd value
\& CDEF:result=value The known value is returned
-.Ve
-.PP
-.Vb 4
+\&
\& For the unknown value, this happens:
\& CDEF:result=value,UN,0,value,IF (value,UN) is true so it becomes 1
\& CDEF:result=1,0,value,IF "IF" sees 1 and returns the 2nd value
\& For the unknown value, this happens:
\& CDEF:result=value,UN,0,value,IF (value,UN) is true so it becomes 1
\& CDEF:result=1,0,value,IF "IF" sees 1 and returns the 2nd value
.PP
Eventually, when all unknown data is removed from the \s-1RRD\s0, you may want
to remove this rule so that unknown data is properly displayed.
.PP
Eventually, when all unknown data is removed from the \s-1RRD\s0, you may want
to remove this rule so that unknown data is properly displayed.
-.Sh "Example: better handling of unknown data, by using time"
+.SS "Example: better handling of unknown data, by using time"
.IX Subsection "Example: better handling of unknown data, by using time"
The above example has one drawback. If you do log unknown data in
your database after installing your new equipment, it will also be
.IX Subsection "Example: better handling of unknown data, by using time"
The above example has one drawback. If you do log unknown data in
your database after installing your new equipment, it will also be
\& where x represents "time>937521357"
\& where a represents the original value
\& where b represents the outcome of the previous example
\& where x represents "time>937521357"
\& where a represents the original value
\& where b represents the outcome of the previous example
-.Ve
-.PP
-.Vb 1
+\&
\& time>937521357 \-\-> TIME,937521357,GT
\& time>937521357 \-\-> TIME,937521357,GT
-.Ve
-.PP
-.Vb 4
+\&
\& if (x) then a else b \-\-> x,a,b,IF
\& substitute x \-\-> TIME,937521357,GT,a,b,IF
\& substitute a \-\-> TIME,937521357,GT,value,b,IF
\& if (x) then a else b \-\-> x,a,b,IF
\& substitute x \-\-> TIME,937521357,GT,a,b,IF
\& substitute a \-\-> TIME,937521357,GT,value,b,IF
.PP
This looks very complex, however, as you can see, it was not too hard to
come up with.
.PP
This looks very complex, however, as you can see, it was not too hard to
come up with.
-.Sh "Example: Pretending weird data isn't there"
+.SS "Example: Pretending weird data isn't there"
.IX Subsection "Example: Pretending weird data isn't there"
Suppose you have a problem that shows up as huge spikes in your graph.
You know this happens and why, so you decide to work around the problem.
.IX Subsection "Example: Pretending weird data isn't there"
Suppose you have a problem that shows up as huge spikes in your graph.
You know this happens and why, so you decide to work around the problem.
\& CDEF:result=number,100000,GT,UNKN,number,IF
\& CDEF:result=number,100000,GT,100000,number,IF
.Ve
\& CDEF:result=number,100000,GT,UNKN,number,IF
\& CDEF:result=number,100000,GT,100000,number,IF
.Ve
-.Sh "Example: working on a certain time span"
+.SS "Example: working on a certain time span"
.IX Subsection "Example: working on a certain time span"
If you want a graph that spans a few weeks, but would only want to
see some routers' data for one week, you need to \*(L"hide\*(R" the rest of
.IX Subsection "Example: working on a certain time span"
If you want a graph that spans a few weeks, but would only want to
see some routers' data for one week, you need to \*(L"hide\*(R" the rest of
.PP
.Vb 2
\& DEF:ds0=router1.rrd:AVERAGE
.PP
.Vb 2
\& DEF:ds0=router1.rrd:AVERAGE
-\& CDEF:ds0modified=TIME,begintime,GE,TIME,endtime,LE,*,UNKN,ds0,IF
+\& CDEF:ds0modified=TIME,begintime,GT,TIME,endtime,LE,*,ds0,UNKN,IF
.Ve
.PP
This will return the value of ds0 if both comparisons return true. You
.Ve
.PP
This will return the value of ds0 if both comparisons return true. You
.Ve
.PP
This will return an \s-1UNKNOWN\s0 if either comparison returns true.
.Ve
.PP
This will return an \s-1UNKNOWN\s0 if either comparison returns true.
-.Sh "Example: You suspect to have problems and want to see unknown data."
+.SS "Example: You suspect to have problems and want to see unknown data."
.IX Subsection "Example: You suspect to have problems and want to see unknown data."
Suppose you add up the number of active users on several terminal servers.
If one of them doesn't give an answer (or an incorrect one) you get \*(L"NaN\*(R"
.IX Subsection "Example: You suspect to have problems and want to see unknown data."
Suppose you add up the number of active users on several terminal servers.
If one of them doesn't give an answer (or an incorrect one) you get \*(L"NaN\*(R"
\& AREA:allusers#0000FF:combined user count
\& AREA:wrongdata#FF0000:unknown data
.Ve
\& AREA:allusers#0000FF:combined user count
\& AREA:wrongdata#FF0000:unknown data
.Ve
-.Sh "Same example useful with STACKed data:"
+.SS "Same example useful with STACKed data:"
.IX Subsection "Same example useful with STACKed data:"
If you use stack in the previous example (as I would do) then you don't
add up the values. Therefore, there is no relationship between the
.IX Subsection "Same example useful with STACKed data:"
If you use stack in the previous example (as I would do) then you don't
add up the values. Therefore, there is no relationship between the
.Ve
.SH "The examples from the RRD graph manual page"
.IX Header "The examples from the RRD graph manual page"
.Ve
.SH "The examples from the RRD graph manual page"
.IX Header "The examples from the RRD graph manual page"
-.Sh "Degrees Celsius vs. Degrees Fahrenheit"
+.SS "Degrees Celsius vs. Degrees Fahrenheit"
.IX Subsection "Degrees Celsius vs. Degrees Fahrenheit"
To convert Celsius into Fahrenheit use the formula
F=9/5*C+32
.IX Subsection "Degrees Celsius vs. Degrees Fahrenheit"
To convert Celsius into Fahrenheit use the formula
F=9/5*C+32
\& 6. push function "plus" and process it
\& the stack contains now the temperature in Fahrenheit
.Ve
\& 6. push function "plus" and process it
\& the stack contains now the temperature in Fahrenheit
.Ve
-.Sh "Changing unknown into zero"
+.SS "Changing unknown into zero"
.IX Subsection "Changing unknown into zero"
.Vb 9
\& rrdtool graph demo.png \-\-title="Demo Graph" \e
.IX Subsection "Changing unknown into zero"
.Vb 9
\& rrdtool graph demo.png \-\-title="Demo Graph" \e
@@ -878,9 +871,9 @@ easy to see that we add \*(L"d\*(R" and \*(L"h\*(R", and multiply the result wit
The end result is that we have added \*(L"idat1\*(R" and \*(L"idat2\*(R" and in the
process we effectively ignored unknown values. The result is multiplied
by eight, most likely to convert bytes/s to bits/s.
The end result is that we have added \*(L"idat1\*(R" and \*(L"idat2\*(R" and in the
process we effectively ignored unknown values. The result is multiplied
by eight, most likely to convert bytes/s to bits/s.
-.Sh "Infinity demo"
+.SS "Infinity demo"
.IX Subsection "Infinity demo"
.IX Subsection "Infinity demo"
-.Vb 13
+.Vb 10
\& rrdtool graph example.png \-\-title="INF demo" \e
\& DEF:val1=some.rrd:ds0:AVERAGE \e
\& DEF:val2=some.rrd:ds1:AVERAGE \e
\& rrdtool graph example.png \-\-title="INF demo" \e
\& DEF:val1=some.rrd:ds0:AVERAGE \e
\& DEF:val2=some.rrd:ds1:AVERAGE \e
the other half of your graph. This can be done in a relatively simple
way: what you need is the \*(L"wipeout\*(R" variable and place a negative
sign before it: \*(L"CDEF:wipeout2=wipeout,\-1,*\*(R"
the other half of your graph. This can be done in a relatively simple
way: what you need is the \*(L"wipeout\*(R" variable and place a negative
sign before it: \*(L"CDEF:wipeout2=wipeout,\-1,*\*(R"
-.Sh "Filtering data"
+.SS "Filtering data"
.IX Subsection "Filtering data"
You may do some complex data filtering:
.PP
.Vb 1
\& MEDIAN FILTER: filters shot noise
.IX Subsection "Filtering data"
You may do some complex data filtering:
.PP
.Vb 1
\& MEDIAN FILTER: filters shot noise
-.Ve
-.PP
-.Vb 7
+\&
\& DEF:var=database.rrd:traffic:AVERAGE
\& CDEF:prev1=PREV(var)
\& CDEF:prev2=PREV(prev1)
\& CDEF:prev3=PREV(prev2)
\& CDEF:median=prev1,prev2,prev3,+,+,3,/
\& LINE3:median#000077:filtered
\& DEF:var=database.rrd:traffic:AVERAGE
\& CDEF:prev1=PREV(var)
\& CDEF:prev2=PREV(prev1)
\& CDEF:prev3=PREV(prev2)
\& CDEF:median=prev1,prev2,prev3,+,+,3,/
\& LINE3:median#000077:filtered
-\& LINE1:prev2#007700:\(aqraw data\(aq
-.Ve
-.PP
-.Vb 1
+\& LINE1:prev2#007700:\*(Aqraw data\*(Aq
+\&
+\&
\& DERIVATE:
\& DERIVATE:
-.Ve
-.PP
-.Vb 7
+\&
\& DEF:var=database.rrd:traffic:AVERAGE
\& CDEF:prev1=PREV(var)
\& CDEF:time=TIME
\& CDEF:prevtime=PREV(time)
\& CDEF:derivate=var,prev1,\-,time,prevtime,\-,/
\& LINE3:derivate#000077:derivate
\& DEF:var=database.rrd:traffic:AVERAGE
\& CDEF:prev1=PREV(var)
\& CDEF:time=TIME
\& CDEF:prevtime=PREV(time)
\& CDEF:derivate=var,prev1,\-,time,prevtime,\-,/
\& LINE3:derivate#000077:derivate
-\& LINE1:var#007700:\(aqraw data\(aq
+\& LINE1:var#007700:\*(Aqraw data\*(Aq
.Ve
.SH "Out of ideas for now"
.IX Header "Out of ideas for now"
.Ve
.SH "Out of ideas for now"
.IX Header "Out of ideas for now"
other people on the RRDtool mailing list. Please let me know if you
find errors in it or if you have trouble understanding it. If you
think there should be an addition, mail me:
other people on the RRDtool mailing list. Please let me know if you
find errors in it or if you have trouble understanding it. If you
think there should be an addition, mail me:
-<alex@ergens.op.het.net>
+<alex@vandenbogaerdt.nl>
.PP
Remember: \fBNo feedback equals no changes!\fR
.SH "SEE ALSO"
.PP
Remember: \fBNo feedback equals no changes!\fR
.SH "SEE ALSO"
.SH "AUTHOR"
.IX Header "AUTHOR"
Alex van den Bogaerdt
.SH "AUTHOR"
.IX Header "AUTHOR"
Alex van den Bogaerdt
-<alex@ergens.op.het.net>
+<alex@vandenbogaerdt.nl>