Merge remote-tracking branch 'upstream/master'

This commit is contained in:
Rouli 2013-01-17 17:33:29 +02:00
commit 446f9f0a0f
64 changed files with 5428 additions and 694 deletions

View File

@ -1,4 +1,48 @@
x January 2013: mitmproxy 0.9:
* Upstream certs mode is now the default.
* Add a WSGI container that lets you host in-proxy web applications.
* Full transparent proxy support for Linux and OSX.
* Introduce netlib, a common codebase for mitmproxy and pathod
(http://github.com/cortesi/netlib).
* Full support for SNI.
* Color palettes for mitmproxy, tailored for light and dark terminal
backgrounds.
* Stream flows to file as responses arrive with the "W" shortcut in
mitmproxy.
* Extend the filter language, including ~d domain match operator, ~a to
match asset flows (js, images, css).
* Follow mode in mitmproxy ("F" shortcut) to "tail" flows as they arrive.
* --dummy-certs option to specify and preserve the dummy certificate
directory.
* Server replay from the current captured buffer.
* Huge improvements in content views. We now have viewers for AMF, HTML,
JSON, Javascript, images, XML, URL-encoded forms, as well as hexadecimal
and raw views.
* Add Set Headers, analagous to replacement hooks. Defines headers that are set
on flows, based on a matching pattern.
* A graphical editor for path components in mitmproxy.
* A small set of standard user-agent strings, which can be used easily in
the header editor.
* Proxy authentication to limit access to mitmproxy
5 April 2012: mitmproxy 0.8:
* Detailed tutorial for Android interception. Some features that land in

View File

@ -1,9 +1,9 @@
__mitmproxy__ is an SSL-capable man-in-the-middle proxy for HTTP. It provides a
console interface that allows traffic flows to be inspected and edited on the
fly.
__mitmproxy__ is an interactive, SSL-capable man-in-the-middle proxy for HTTP
with a console interface.
__mitmdump__ is the command-line version of mitmproxy, with the same
functionality but without the user interface. Think tcpdump for HTTP.
__mitmdump__ is the command-line version of mitmproxy. Think tcpdump for HTTP.
__libmproxy__ is the library that mitmproxy and mitmdump are built on.
Complete documentation and a set of practical tutorials is included in the
distribution package, and is also available at
@ -18,14 +18,15 @@ Features
- Replay the client-side of an HTTP conversations.
- Replay HTTP responses of a previously recorded server.
- Reverse proxy mode to forward traffic to a specified server.
- Transparent proxy mode on OSX and Linux.
- Make scripted changes to HTTP traffic using Python.
- SSL certificates for interception are generated on the fly.
- And much, much more.
Download
--------
Releases and rendered documentation can be found on the mitmproxy website:
Releases and documentation can be found on the mitmproxy website:
[mitmproxy.org](http://mitmproxy.org)
@ -42,7 +43,7 @@ Come join us in the #mitmproxy channel on the OFTC IRC network
We also have a mailing list, hosted here:
http://groups.google.com/group/mitmproxy
[groups.google.com/group/mitmproxy](http://groups.google.com/group/mitmproxy)
Requirements
@ -51,17 +52,17 @@ Requirements
* [Python](http://www.python.org) 2.7.x.
* [PyOpenSSL](http://pypi.python.org/pypi/pyOpenSSL) 0.13 or newer.
* [pyasn1](http://pypi.python.org/pypi/pyasn1) 0.1.2 or newer.
* [urwid](http://excess.org/urwid/) version 0.9.8 or newer.
* [urwid](http://excess.org/urwid/) version 1.1 or newer.
* [PIL](http://www.pythonware.com/products/pil/) version 1.1 or newer.
* [lxml](http://lxml.de/) version 2.3 or newer.
* [netlib](http://pypi.python.org/pypi/netlib) 0.1 or newer.
* [netlib](http://pypi.python.org/pypi/netlib) 0.2.2 or newer.
The following auxiliary components may be needed if you plan to hack on
mitmproxy:
* The test suite uses the [nose](http://readthedocs.org/docs/nose/en/latest/) unit testing
framework and requires [human_curl](https://github.com/Lispython/human_curl) and
[pathod](http://pypi.python.org/pypi/pathod).
[pathod](http://pathod.org).
* Rendering the documentation requires [countershape](http://github.com/cortesi/countershape).
__mitmproxy__ is tested and developed on OSX, Linux and OpenBSD. Windows is not

View File

@ -1,84 +1,11 @@
**mitmproxy** is an SSL-capable man-in-the-middle proxy for HTTP. It provides a
console interface that allows traffic flows to be inspected and edited on the
fly.
**mitmproxy** is an interactive, SSL-capable man-in-the-middle proxy for HTTP
with a console interface.
**mitmdump** is the command-line version of mitmproxy, with the same
functionality but without the user interface. Think tcpdump for HTTP.
**mitmdump** is the command-line version of mitmproxy. Think tcpdump for HTTP.
**libmproxy** is the library that mitmproxy and mitmdump are built on.
Complete documentation and a set of practical tutorials is included in the
distribution package, and is also available at mitmproxy.org_.
Features
--------
- Intercept HTTP requests and responses and modify them on the fly.
- Save complete HTTP conversations for later replay and analysis.
- Replay the client-side of an HTTP conversations.
- Replay HTTP responses of a previously recorded server.
- Reverse proxy mode to forward traffic to a specified server.
- Make scripted changes to HTTP traffic using Python.
- SSL certificates for interception are generated on the fly.
Download
--------
Releases and rendered documentation can be found on the mitmproxy website:
mitmproxy.org_
Source is hosted on github:
`github.com/cortesi/mitmproxy`_
Community
---------
Come join us in the #mitmproxy channel on the OFTC IRC network
(irc.oftc.net, port 6667).
We also have a mailing list, hosted here:
http://groups.google.com/group/mitmproxy
Requirements
------------
* Python_ 2.7.x.
* PyOpenSSL_ 0.13 or newer.
* pyasn1_ 0.1.2 or newer.
* urwid_ version 0.9.8 or newer.
* PIL_ version 1.1 or newer.
* lxml_ version 2.3 or newer.
The following auxiliary components may be needed if you plan to hack on
mitmproxy:
* The test suite uses the nose_ unit testing
framework.
* Rendering the documentation requires countershape_.
**mitmproxy** is tested and developed on OSX, Linux and OpenBSD. Windows is not
supported at the moment.
You should also make sure that your console environment is set up with the
following:
* EDITOR environment variable to determine the external editor.
* PAGER environment variable to determine the external pager.
* Appropriate entries in your mailcap files to determine external
viewers for request and response contents.
.. _mitmproxy.org: http://mitmproxy.org
.. _github.com/cortesi/mitmproxy: http://github.com/cortesi/mitmproxy
.. _python: http://www.python.org
.. _PyOpenSSL: http://pypi.python.org/pypi/pyOpenSSL
.. _pyasn1: http://pypi.python.org/pypi/pyasn1
.. _PIL: http://www.pythonware.com/products/pil/
.. _lxml: http://lxml.de/
.. _urwid: http://excess.org/urwid/
.. _nose: http://readthedocs.org/docs/nose/en/latest/
.. _countershape: http://github.com/cortesi/countershape

940
doc-src/01-bootstrap.min.css vendored Normal file
View File

@ -0,0 +1,940 @@
@import url('https://fonts.googleapis.com/css?family=Open+Sans:400italic,700italic,400,700');
article,aside,details,figcaption,figure,footer,header,hgroup,nav,section{display:block;}
audio,canvas,video{display:inline-block;*display:inline;*zoom:1;}
audio:not([controls]){display:none;}
html{font-size:100%;-webkit-text-size-adjust:100%;-ms-text-size-adjust:100%;}
a:focus{outline:thin dotted #333;outline:5px auto -webkit-focus-ring-color;outline-offset:-2px;}
a:hover,a:active{outline:0;}
sub,sup{position:relative;font-size:75%;line-height:0;vertical-align:baseline;}
sup{top:-0.5em;}
sub{bottom:-0.25em;}
img{max-width:100%;width:auto\9;height:auto;vertical-align:middle;border:0;-ms-interpolation-mode:bicubic;}
#map_canvas img,.google-maps img{max-width:none;}
button,input,select,textarea{margin:0;font-size:100%;vertical-align:middle;}
button,input{*overflow:visible;line-height:normal;}
button::-moz-focus-inner,input::-moz-focus-inner{padding:0;border:0;}
button,html input[type="button"],input[type="reset"],input[type="submit"]{-webkit-appearance:button;cursor:pointer;}
label,select,button,input[type="button"],input[type="reset"],input[type="submit"],input[type="radio"],input[type="checkbox"]{cursor:pointer;}
input[type="search"]{-webkit-box-sizing:content-box;-moz-box-sizing:content-box;box-sizing:content-box;-webkit-appearance:textfield;}
input[type="search"]::-webkit-search-decoration,input[type="search"]::-webkit-search-cancel-button{-webkit-appearance:none;}
textarea{overflow:auto;vertical-align:top;}
@media print{*{text-shadow:none !important;color:#000 !important;background:transparent !important;box-shadow:none !important;} a,a:visited{text-decoration:underline;} a[href]:after{content:" (" attr(href) ")";} abbr[title]:after{content:" (" attr(title) ")";} .ir a:after,a[href^="javascript:"]:after,a[href^="#"]:after{content:"";} pre,blockquote{border:1px solid #999;page-break-inside:avoid;} thead{display:table-header-group;} tr,img{page-break-inside:avoid;} img{max-width:100% !important;} @page {margin:0.5cm;}p,h2,h3{orphans:3;widows:3;} h2,h3{page-break-after:avoid;}}.clearfix{*zoom:1;}.clearfix:before,.clearfix:after{display:table;content:"";line-height:0;}
.clearfix:after{clear:both;}
.hide-text{font:0/0 a;color:transparent;text-shadow:none;background-color:transparent;border:0;}
.input-block-level{display:block;width:100%;min-height:30px;-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box;}
body{margin:0;font-family:"Open Sans",Calibri,Candara,Arial,sans-serif;font-size:14px;line-height:20px;color:#555555;background-color:#ffffff;}
a{color:#007fff;text-decoration:none;}
a:hover{color:#0066cc;text-decoration:underline;}
.img-rounded{-webkit-border-radius:6px;-moz-border-radius:6px;border-radius:6px;}
.img-polaroid{padding:4px;background-color:#fff;border:1px solid #ccc;border:1px solid rgba(0, 0, 0, 0.2);-webkit-box-shadow:0 1px 3px rgba(0, 0, 0, 0.1);-moz-box-shadow:0 1px 3px rgba(0, 0, 0, 0.1);box-shadow:0 1px 3px rgba(0, 0, 0, 0.1);}
.img-circle{-webkit-border-radius:500px;-moz-border-radius:500px;border-radius:500px;}
.row{margin-left:-20px;*zoom:1;}.row:before,.row:after{display:table;content:"";line-height:0;}
.row:after{clear:both;}
[class*="span"]{float:left;min-height:1px;margin-left:20px;}
.container,.navbar-static-top .container,.navbar-fixed-top .container,.navbar-fixed-bottom .container{width:940px;}
.span12{width:940px;}
.span11{width:860px;}
.span10{width:780px;}
.span9{width:700px;}
.span8{width:620px;}
.span7{width:540px;}
.span6{width:460px;}
.span5{width:380px;}
.span4{width:300px;}
.span3{width:220px;}
.span2{width:140px;}
.span1{width:60px;}
.offset12{margin-left:980px;}
.offset11{margin-left:900px;}
.offset10{margin-left:820px;}
.offset9{margin-left:740px;}
.offset8{margin-left:660px;}
.offset7{margin-left:580px;}
.offset6{margin-left:500px;}
.offset5{margin-left:420px;}
.offset4{margin-left:340px;}
.offset3{margin-left:260px;}
.offset2{margin-left:180px;}
.offset1{margin-left:100px;}
.row-fluid{width:100%;*zoom:1;}.row-fluid:before,.row-fluid:after{display:table;content:"";line-height:0;}
.row-fluid:after{clear:both;}
.row-fluid [class*="span"]{display:block;width:100%;min-height:30px;-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box;float:left;margin-left:2.127659574468085%;*margin-left:2.074468085106383%;}
.row-fluid [class*="span"]:first-child{margin-left:0;}
.row-fluid .controls-row [class*="span"]+[class*="span"]{margin-left:2.127659574468085%;}
.row-fluid .span12{width:100%;*width:99.94680851063829%;}
.row-fluid .span11{width:91.48936170212765%;*width:91.43617021276594%;}
.row-fluid .span10{width:82.97872340425532%;*width:82.92553191489361%;}
.row-fluid .span9{width:74.46808510638297%;*width:74.41489361702126%;}
.row-fluid .span8{width:65.95744680851064%;*width:65.90425531914893%;}
.row-fluid .span7{width:57.44680851063829%;*width:57.39361702127659%;}
.row-fluid .span6{width:48.93617021276595%;*width:48.88297872340425%;}
.row-fluid .span5{width:40.42553191489362%;*width:40.37234042553192%;}
.row-fluid .span4{width:31.914893617021278%;*width:31.861702127659576%;}
.row-fluid .span3{width:23.404255319148934%;*width:23.351063829787233%;}
.row-fluid .span2{width:14.893617021276595%;*width:14.840425531914894%;}
.row-fluid .span1{width:6.382978723404255%;*width:6.329787234042553%;}
.row-fluid .offset12{margin-left:104.25531914893617%;*margin-left:104.14893617021275%;}
.row-fluid .offset12:first-child{margin-left:102.12765957446808%;*margin-left:102.02127659574467%;}
.row-fluid .offset11{margin-left:95.74468085106382%;*margin-left:95.6382978723404%;}
.row-fluid .offset11:first-child{margin-left:93.61702127659574%;*margin-left:93.51063829787232%;}
.row-fluid .offset10{margin-left:87.23404255319149%;*margin-left:87.12765957446807%;}
.row-fluid .offset10:first-child{margin-left:85.1063829787234%;*margin-left:84.99999999999999%;}
.row-fluid .offset9{margin-left:78.72340425531914%;*margin-left:78.61702127659572%;}
.row-fluid .offset9:first-child{margin-left:76.59574468085106%;*margin-left:76.48936170212764%;}
.row-fluid .offset8{margin-left:70.2127659574468%;*margin-left:70.10638297872339%;}
.row-fluid .offset8:first-child{margin-left:68.08510638297872%;*margin-left:67.9787234042553%;}
.row-fluid .offset7{margin-left:61.70212765957446%;*margin-left:61.59574468085106%;}
.row-fluid .offset7:first-child{margin-left:59.574468085106375%;*margin-left:59.46808510638297%;}
.row-fluid .offset6{margin-left:53.191489361702125%;*margin-left:53.085106382978715%;}
.row-fluid .offset6:first-child{margin-left:51.063829787234035%;*margin-left:50.95744680851063%;}
.row-fluid .offset5{margin-left:44.68085106382979%;*margin-left:44.57446808510638%;}
.row-fluid .offset5:first-child{margin-left:42.5531914893617%;*margin-left:42.4468085106383%;}
.row-fluid .offset4{margin-left:36.170212765957444%;*margin-left:36.06382978723405%;}
.row-fluid .offset4:first-child{margin-left:34.04255319148936%;*margin-left:33.93617021276596%;}
.row-fluid .offset3{margin-left:27.659574468085104%;*margin-left:27.5531914893617%;}
.row-fluid .offset3:first-child{margin-left:25.53191489361702%;*margin-left:25.425531914893618%;}
.row-fluid .offset2{margin-left:19.148936170212764%;*margin-left:19.04255319148936%;}
.row-fluid .offset2:first-child{margin-left:17.02127659574468%;*margin-left:16.914893617021278%;}
.row-fluid .offset1{margin-left:10.638297872340425%;*margin-left:10.53191489361702%;}
.row-fluid .offset1:first-child{margin-left:8.51063829787234%;*margin-left:8.404255319148938%;}
[class*="span"].hide,.row-fluid [class*="span"].hide{display:none;}
[class*="span"].pull-right,.row-fluid [class*="span"].pull-right{float:right;}
.container{margin-right:auto;margin-left:auto;*zoom:1;}.container:before,.container:after{display:table;content:"";line-height:0;}
.container:after{clear:both;}
.container-fluid{padding-right:20px;padding-left:20px;*zoom:1;}.container-fluid:before,.container-fluid:after{display:table;content:"";line-height:0;}
.container-fluid:after{clear:both;}
p{margin:0 0 10px;}
.lead{margin-bottom:20px;font-size:21px;font-weight:200;line-height:30px;}
small{font-size:85%;}
strong{font-weight:bold;}
em{font-style:italic;}
cite{font-style:normal;}
.muted{color:#dfdfdf;}
a.muted:hover{color:#c6c6c6;}
.text-warning{color:#ffffff;}
a.text-warning:hover{color:#e6e6e6;}
.text-error{color:#ffffff;}
a.text-error:hover{color:#e6e6e6;}
.text-info{color:#ffffff;}
a.text-info:hover{color:#e6e6e6;}
.text-success{color:#ffffff;}
a.text-success:hover{color:#e6e6e6;}
h1,h2,h3,h4,h5,h6{margin:10px 0;font-family:inherit;font-weight:300;line-height:20px;color:#080808;text-rendering:optimizelegibility;}h1 small,h2 small,h3 small,h4 small,h5 small,h6 small{font-weight:normal;line-height:1;color:#dfdfdf;}
h1,h2,h3{line-height:40px;}
h1{font-size:38.5px;}
h2{font-size:31.5px;}
h3{font-size:24.5px;}
h4{font-size:17.5px;}
h5{font-size:14px;}
h6{font-size:11.9px;}
h1 small{font-size:24.5px;}
h2 small{font-size:17.5px;}
h3 small{font-size:14px;}
h4 small{font-size:14px;}
.page-header{padding-bottom:9px;margin:20px 0 30px;border-bottom:1px solid #eeeeee;}
ul,ol{padding:0;margin:0 0 10px 25px;}
ul ul,ul ol,ol ol,ol ul{margin-bottom:0;}
li{line-height:20px;}
ul.unstyled,ol.unstyled{margin-left:0;list-style:none;}
ul.inline,ol.inline{margin-left:0;list-style:none;}ul.inline >li,ol.inline >li{display:inline-block;padding-left:5px;padding-right:5px;}
dl{margin-bottom:20px;}
dt,dd{line-height:20px;}
dt{font-weight:bold;}
dd{margin-left:10px;}
.dl-horizontal{*zoom:1;}.dl-horizontal:before,.dl-horizontal:after{display:table;content:"";line-height:0;}
.dl-horizontal:after{clear:both;}
.dl-horizontal dt{float:left;width:160px;clear:left;text-align:right;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;}
.dl-horizontal dd{margin-left:180px;}
hr{margin:20px 0;border:0;border-top:1px solid #eeeeee;border-bottom:1px solid #ffffff;}
abbr[title],abbr[data-original-title]{cursor:help;border-bottom:1px dotted #dfdfdf;}
abbr.initialism{font-size:90%;text-transform:uppercase;}
blockquote{padding:0 0 0 15px;margin:0 0 20px;border-left:5px solid #eeeeee;}blockquote p{margin-bottom:0;font-size:16px;font-weight:300;line-height:25px;}
blockquote small{display:block;line-height:20px;color:#dfdfdf;}blockquote small:before{content:'\2014 \00A0';}
blockquote.pull-right{float:right;padding-right:15px;padding-left:0;border-right:5px solid #eeeeee;border-left:0;}blockquote.pull-right p,blockquote.pull-right small{text-align:right;}
blockquote.pull-right small:before{content:'';}
blockquote.pull-right small:after{content:'\00A0 \2014';}
q:before,q:after,blockquote:before,blockquote:after{content:"";}
address{display:block;margin-bottom:20px;font-style:normal;line-height:20px;}
code,pre{padding:0 3px 2px;font-family:Monaco,Menlo,Consolas,"Courier New",monospace;font-size:12px;color:#999999;-webkit-border-radius:3px;-moz-border-radius:3px;border-radius:3px;}
code{padding:2px 4px;color:#d14;background-color:#f7f7f9;border:1px solid #e1e1e8;white-space:nowrap;}
pre{display:block;padding:9.5px;margin:0 0 10px;font-size:13px;line-height:20px;word-break:break-all;word-wrap:break-word;white-space:pre;white-space:pre-wrap;background-color:#f5f5f5;border:1px solid #ccc;border:1px solid rgba(0, 0, 0, 0.15);-webkit-border-radius:0px;-moz-border-radius:0px;border-radius:0px;}pre.prettyprint{margin-bottom:20px;}
pre code{padding:0;color:inherit;white-space:pre;white-space:pre-wrap;background-color:transparent;border:0;}
.pre-scrollable{max-height:340px;overflow-y:scroll;}
form{margin:0 0 20px;}
fieldset{padding:0;margin:0;border:0;}
legend{display:block;width:100%;padding:0;margin-bottom:20px;font-size:21px;line-height:40px;color:#999999;border:0;border-bottom:1px solid #e5e5e5;}legend small{font-size:15px;color:#dfdfdf;}
label,input,button,select,textarea{font-size:14px;font-weight:normal;line-height:20px;}
input,button,select,textarea{font-family:"Open Sans",Calibri,Candara,Arial,sans-serif;}
label{display:block;margin-bottom:5px;}
select,textarea,input[type="text"],input[type="password"],input[type="datetime"],input[type="datetime-local"],input[type="date"],input[type="month"],input[type="time"],input[type="week"],input[type="number"],input[type="email"],input[type="url"],input[type="search"],input[type="tel"],input[type="color"],.uneditable-input{display:inline-block;height:20px;padding:4px 6px;margin-bottom:10px;font-size:14px;line-height:20px;color:#bbbbbb;-webkit-border-radius:0px;-moz-border-radius:0px;border-radius:0px;vertical-align:middle;}
input,textarea,.uneditable-input{width:206px;}
textarea{height:auto;}
textarea,input[type="text"],input[type="password"],input[type="datetime"],input[type="datetime-local"],input[type="date"],input[type="month"],input[type="time"],input[type="week"],input[type="number"],input[type="email"],input[type="url"],input[type="search"],input[type="tel"],input[type="color"],.uneditable-input{background-color:#ffffff;border:1px solid #bbbbbb;-webkit-box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075);-moz-box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075);box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075);-webkit-transition:border linear .2s, box-shadow linear .2s;-moz-transition:border linear .2s, box-shadow linear .2s;-o-transition:border linear .2s, box-shadow linear .2s;transition:border linear .2s, box-shadow linear .2s;}textarea:focus,input[type="text"]:focus,input[type="password"]:focus,input[type="datetime"]:focus,input[type="datetime-local"]:focus,input[type="date"]:focus,input[type="month"]:focus,input[type="time"]:focus,input[type="week"]:focus,input[type="number"]:focus,input[type="email"]:focus,input[type="url"]:focus,input[type="search"]:focus,input[type="tel"]:focus,input[type="color"]:focus,.uneditable-input:focus{border-color:rgba(82, 168, 236, 0.8);outline:0;outline:thin dotted \9;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(82,168,236,.6);-moz-box-shadow:inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(82,168,236,.6);box-shadow:inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(82,168,236,.6);}
input[type="radio"],input[type="checkbox"]{margin:4px 0 0;*margin-top:0;margin-top:1px \9;line-height:normal;}
input[type="file"],input[type="image"],input[type="submit"],input[type="reset"],input[type="button"],input[type="radio"],input[type="checkbox"]{width:auto;}
select,input[type="file"]{height:30px;*margin-top:4px;line-height:30px;}
select{width:220px;border:1px solid #bbbbbb;background-color:#ffffff;}
select[multiple],select[size]{height:auto;}
select:focus,input[type="file"]:focus,input[type="radio"]:focus,input[type="checkbox"]:focus{outline:thin dotted #333;outline:5px auto -webkit-focus-ring-color;outline-offset:-2px;}
.uneditable-input,.uneditable-textarea{color:#dfdfdf;background-color:#fcfcfc;border-color:#bbbbbb;-webkit-box-shadow:inset 0 1px 2px rgba(0, 0, 0, 0.025);-moz-box-shadow:inset 0 1px 2px rgba(0, 0, 0, 0.025);box-shadow:inset 0 1px 2px rgba(0, 0, 0, 0.025);cursor:not-allowed;}
.uneditable-input{overflow:hidden;white-space:nowrap;}
.uneditable-textarea{width:auto;height:auto;}
input:-moz-placeholder,textarea:-moz-placeholder{color:#bbbbbb;}
input:-ms-input-placeholder,textarea:-ms-input-placeholder{color:#bbbbbb;}
input::-webkit-input-placeholder,textarea::-webkit-input-placeholder{color:#bbbbbb;}
.radio,.checkbox{min-height:20px;padding-left:20px;}
.radio input[type="radio"],.checkbox input[type="checkbox"]{float:left;margin-left:-20px;}
.controls>.radio:first-child,.controls>.checkbox:first-child{padding-top:5px;}
.radio.inline,.checkbox.inline{display:inline-block;padding-top:5px;margin-bottom:0;vertical-align:middle;}
.radio.inline+.radio.inline,.checkbox.inline+.checkbox.inline{margin-left:10px;}
.input-mini{width:60px;}
.input-small{width:90px;}
.input-medium{width:150px;}
.input-large{width:210px;}
.input-xlarge{width:270px;}
.input-xxlarge{width:530px;}
input[class*="span"],select[class*="span"],textarea[class*="span"],.uneditable-input[class*="span"],.row-fluid input[class*="span"],.row-fluid select[class*="span"],.row-fluid textarea[class*="span"],.row-fluid .uneditable-input[class*="span"]{float:none;margin-left:0;}
.input-append input[class*="span"],.input-append .uneditable-input[class*="span"],.input-prepend input[class*="span"],.input-prepend .uneditable-input[class*="span"],.row-fluid input[class*="span"],.row-fluid select[class*="span"],.row-fluid textarea[class*="span"],.row-fluid .uneditable-input[class*="span"],.row-fluid .input-prepend [class*="span"],.row-fluid .input-append [class*="span"]{display:inline-block;}
input,textarea,.uneditable-input{margin-left:0;}
.controls-row [class*="span"]+[class*="span"]{margin-left:20px;}
input.span12, textarea.span12, .uneditable-input.span12{width:926px;}
input.span11, textarea.span11, .uneditable-input.span11{width:846px;}
input.span10, textarea.span10, .uneditable-input.span10{width:766px;}
input.span9, textarea.span9, .uneditable-input.span9{width:686px;}
input.span8, textarea.span8, .uneditable-input.span8{width:606px;}
input.span7, textarea.span7, .uneditable-input.span7{width:526px;}
input.span6, textarea.span6, .uneditable-input.span6{width:446px;}
input.span5, textarea.span5, .uneditable-input.span5{width:366px;}
input.span4, textarea.span4, .uneditable-input.span4{width:286px;}
input.span3, textarea.span3, .uneditable-input.span3{width:206px;}
input.span2, textarea.span2, .uneditable-input.span2{width:126px;}
input.span1, textarea.span1, .uneditable-input.span1{width:46px;}
.controls-row{*zoom:1;}.controls-row:before,.controls-row:after{display:table;content:"";line-height:0;}
.controls-row:after{clear:both;}
.controls-row [class*="span"],.row-fluid .controls-row [class*="span"]{float:left;}
.controls-row .checkbox[class*="span"],.controls-row .radio[class*="span"]{padding-top:5px;}
input[disabled],select[disabled],textarea[disabled],input[readonly],select[readonly],textarea[readonly]{cursor:not-allowed;background-color:#eeeeee;}
input[type="radio"][disabled],input[type="checkbox"][disabled],input[type="radio"][readonly],input[type="checkbox"][readonly]{background-color:transparent;}
.control-group.warning .control-label,.control-group.warning .help-block,.control-group.warning .help-inline{color:#ffffff;}
.control-group.warning .checkbox,.control-group.warning .radio,.control-group.warning input,.control-group.warning select,.control-group.warning textarea{color:#ffffff;}
.control-group.warning input,.control-group.warning select,.control-group.warning textarea{border-color:#ffffff;-webkit-box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075);-moz-box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075);box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075);}.control-group.warning input:focus,.control-group.warning select:focus,.control-group.warning textarea:focus{border-color:#e6e6e6;-webkit-box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075),0 0 6px #ffffff;-moz-box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075),0 0 6px #ffffff;box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075),0 0 6px #ffffff;}
.control-group.warning .input-prepend .add-on,.control-group.warning .input-append .add-on{color:#ffffff;background-color:#ff7518;border-color:#ffffff;}
.control-group.error .control-label,.control-group.error .help-block,.control-group.error .help-inline{color:#ffffff;}
.control-group.error .checkbox,.control-group.error .radio,.control-group.error input,.control-group.error select,.control-group.error textarea{color:#ffffff;}
.control-group.error input,.control-group.error select,.control-group.error textarea{border-color:#ffffff;-webkit-box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075);-moz-box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075);box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075);}.control-group.error input:focus,.control-group.error select:focus,.control-group.error textarea:focus{border-color:#e6e6e6;-webkit-box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075),0 0 6px #ffffff;-moz-box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075),0 0 6px #ffffff;box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075),0 0 6px #ffffff;}
.control-group.error .input-prepend .add-on,.control-group.error .input-append .add-on{color:#ffffff;background-color:#ff0039;border-color:#ffffff;}
.control-group.success .control-label,.control-group.success .help-block,.control-group.success .help-inline{color:#ffffff;}
.control-group.success .checkbox,.control-group.success .radio,.control-group.success input,.control-group.success select,.control-group.success textarea{color:#ffffff;}
.control-group.success input,.control-group.success select,.control-group.success textarea{border-color:#ffffff;-webkit-box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075);-moz-box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075);box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075);}.control-group.success input:focus,.control-group.success select:focus,.control-group.success textarea:focus{border-color:#e6e6e6;-webkit-box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075),0 0 6px #ffffff;-moz-box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075),0 0 6px #ffffff;box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075),0 0 6px #ffffff;}
.control-group.success .input-prepend .add-on,.control-group.success .input-append .add-on{color:#ffffff;background-color:#3fb618;border-color:#ffffff;}
.control-group.info .control-label,.control-group.info .help-block,.control-group.info .help-inline{color:#ffffff;}
.control-group.info .checkbox,.control-group.info .radio,.control-group.info input,.control-group.info select,.control-group.info textarea{color:#ffffff;}
.control-group.info input,.control-group.info select,.control-group.info textarea{border-color:#ffffff;-webkit-box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075);-moz-box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075);box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075);}.control-group.info input:focus,.control-group.info select:focus,.control-group.info textarea:focus{border-color:#e6e6e6;-webkit-box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075),0 0 6px #ffffff;-moz-box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075),0 0 6px #ffffff;box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.075),0 0 6px #ffffff;}
.control-group.info .input-prepend .add-on,.control-group.info .input-append .add-on{color:#ffffff;background-color:#9954bb;border-color:#ffffff;}
input:focus:invalid,textarea:focus:invalid,select:focus:invalid{color:#b94a48;border-color:#ee5f5b;}input:focus:invalid:focus,textarea:focus:invalid:focus,select:focus:invalid:focus{border-color:#e9322d;-webkit-box-shadow:0 0 6px #f8b9b7;-moz-box-shadow:0 0 6px #f8b9b7;box-shadow:0 0 6px #f8b9b7;}
.form-actions{padding:19px 20px 20px;margin-top:20px;margin-bottom:20px;background-color:#f5f5f5;border-top:1px solid #e5e5e5;*zoom:1;}.form-actions:before,.form-actions:after{display:table;content:"";line-height:0;}
.form-actions:after{clear:both;}
.help-block,.help-inline{color:#7b7b7b;}
.help-block{display:block;margin-bottom:10px;}
.help-inline{display:inline-block;*display:inline;*zoom:1;vertical-align:middle;padding-left:5px;}
.input-append,.input-prepend{margin-bottom:5px;font-size:0;white-space:nowrap;}.input-append input,.input-prepend input,.input-append select,.input-prepend select,.input-append .uneditable-input,.input-prepend .uneditable-input,.input-append .dropdown-menu,.input-prepend .dropdown-menu{font-size:14px;}
.input-append input,.input-prepend input,.input-append select,.input-prepend select,.input-append .uneditable-input,.input-prepend .uneditable-input{position:relative;margin-bottom:0;*margin-left:0;vertical-align:top;-webkit-border-radius:0 0px 0px 0;-moz-border-radius:0 0px 0px 0;border-radius:0 0px 0px 0;}.input-append input:focus,.input-prepend input:focus,.input-append select:focus,.input-prepend select:focus,.input-append .uneditable-input:focus,.input-prepend .uneditable-input:focus{z-index:2;}
.input-append .add-on,.input-prepend .add-on{display:inline-block;width:auto;height:20px;min-width:16px;padding:4px 5px;font-size:14px;font-weight:normal;line-height:20px;text-align:center;text-shadow:0 1px 0 #ffffff;background-color:#eeeeee;border:1px solid #ccc;}
.input-append .add-on,.input-prepend .add-on,.input-append .btn,.input-prepend .btn,.input-append .btn-group>.dropdown-toggle,.input-prepend .btn-group>.dropdown-toggle{vertical-align:top;-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;}
.input-append .active,.input-prepend .active{background-color:#96ed7a;border-color:#3fb618;}
.input-prepend .add-on,.input-prepend .btn{margin-right:-1px;}
.input-prepend .add-on:first-child,.input-prepend .btn:first-child{-webkit-border-radius:0px 0 0 0px;-moz-border-radius:0px 0 0 0px;border-radius:0px 0 0 0px;}
.input-append input,.input-append select,.input-append .uneditable-input{-webkit-border-radius:0px 0 0 0px;-moz-border-radius:0px 0 0 0px;border-radius:0px 0 0 0px;}.input-append input+.btn-group .btn:last-child,.input-append select+.btn-group .btn:last-child,.input-append .uneditable-input+.btn-group .btn:last-child{-webkit-border-radius:0 0px 0px 0;-moz-border-radius:0 0px 0px 0;border-radius:0 0px 0px 0;}
.input-append .add-on,.input-append .btn,.input-append .btn-group{margin-left:-1px;}
.input-append .add-on:last-child,.input-append .btn:last-child,.input-append .btn-group:last-child>.dropdown-toggle{-webkit-border-radius:0 0px 0px 0;-moz-border-radius:0 0px 0px 0;border-radius:0 0px 0px 0;}
.input-prepend.input-append input,.input-prepend.input-append select,.input-prepend.input-append .uneditable-input{-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;}.input-prepend.input-append input+.btn-group .btn,.input-prepend.input-append select+.btn-group .btn,.input-prepend.input-append .uneditable-input+.btn-group .btn{-webkit-border-radius:0 0px 0px 0;-moz-border-radius:0 0px 0px 0;border-radius:0 0px 0px 0;}
.input-prepend.input-append .add-on:first-child,.input-prepend.input-append .btn:first-child{margin-right:-1px;-webkit-border-radius:0px 0 0 0px;-moz-border-radius:0px 0 0 0px;border-radius:0px 0 0 0px;}
.input-prepend.input-append .add-on:last-child,.input-prepend.input-append .btn:last-child{margin-left:-1px;-webkit-border-radius:0 0px 0px 0;-moz-border-radius:0 0px 0px 0;border-radius:0 0px 0px 0;}
.input-prepend.input-append .btn-group:first-child{margin-left:0;}
input.search-query{padding-right:14px;padding-right:4px \9;padding-left:14px;padding-left:4px \9;margin-bottom:0;-webkit-border-radius:15px;-moz-border-radius:15px;border-radius:15px;}
.form-search .input-append .search-query,.form-search .input-prepend .search-query{-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;}
.form-search .input-append .search-query{-webkit-border-radius:14px 0 0 14px;-moz-border-radius:14px 0 0 14px;border-radius:14px 0 0 14px;}
.form-search .input-append .btn{-webkit-border-radius:0 14px 14px 0;-moz-border-radius:0 14px 14px 0;border-radius:0 14px 14px 0;}
.form-search .input-prepend .search-query{-webkit-border-radius:0 14px 14px 0;-moz-border-radius:0 14px 14px 0;border-radius:0 14px 14px 0;}
.form-search .input-prepend .btn{-webkit-border-radius:14px 0 0 14px;-moz-border-radius:14px 0 0 14px;border-radius:14px 0 0 14px;}
.form-search input,.form-inline input,.form-horizontal input,.form-search textarea,.form-inline textarea,.form-horizontal textarea,.form-search select,.form-inline select,.form-horizontal select,.form-search .help-inline,.form-inline .help-inline,.form-horizontal .help-inline,.form-search .uneditable-input,.form-inline .uneditable-input,.form-horizontal .uneditable-input,.form-search .input-prepend,.form-inline .input-prepend,.form-horizontal .input-prepend,.form-search .input-append,.form-inline .input-append,.form-horizontal .input-append{display:inline-block;*display:inline;*zoom:1;margin-bottom:0;vertical-align:middle;}
.form-search .hide,.form-inline .hide,.form-horizontal .hide{display:none;}
.form-search label,.form-inline label,.form-search .btn-group,.form-inline .btn-group{display:inline-block;}
.form-search .input-append,.form-inline .input-append,.form-search .input-prepend,.form-inline .input-prepend{margin-bottom:0;}
.form-search .radio,.form-search .checkbox,.form-inline .radio,.form-inline .checkbox{padding-left:0;margin-bottom:0;vertical-align:middle;}
.form-search .radio input[type="radio"],.form-search .checkbox input[type="checkbox"],.form-inline .radio input[type="radio"],.form-inline .checkbox input[type="checkbox"]{float:left;margin-right:3px;margin-left:0;}
.control-group{margin-bottom:10px;}
legend+.control-group{margin-top:20px;-webkit-margin-top-collapse:separate;}
.form-horizontal .control-group{margin-bottom:20px;*zoom:1;}.form-horizontal .control-group:before,.form-horizontal .control-group:after{display:table;content:"";line-height:0;}
.form-horizontal .control-group:after{clear:both;}
.form-horizontal .control-label{float:left;width:160px;padding-top:5px;text-align:right;}
.form-horizontal .controls{*display:inline-block;*padding-left:20px;margin-left:180px;*margin-left:0;}.form-horizontal .controls:first-child{*padding-left:180px;}
.form-horizontal .help-block{margin-bottom:0;}
.form-horizontal input+.help-block,.form-horizontal select+.help-block,.form-horizontal textarea+.help-block,.form-horizontal .uneditable-input+.help-block,.form-horizontal .input-prepend+.help-block,.form-horizontal .input-append+.help-block{margin-top:10px;}
.form-horizontal .form-actions{padding-left:180px;}
table{max-width:100%;background-color:transparent;border-collapse:collapse;border-spacing:0;}
.table{width:100%;margin-bottom:20px;}.table th,.table td{padding:8px;line-height:20px;text-align:left;vertical-align:top;border-top:1px solid #dddddd;}
.table th{font-weight:bold;}
.table thead th{vertical-align:bottom;}
.table caption+thead tr:first-child th,.table caption+thead tr:first-child td,.table colgroup+thead tr:first-child th,.table colgroup+thead tr:first-child td,.table thead:first-child tr:first-child th,.table thead:first-child tr:first-child td{border-top:0;}
.table tbody+tbody{border-top:2px solid #dddddd;}
.table .table{background-color:#ffffff;}
.table-condensed th,.table-condensed td{padding:4px 5px;}
.table-bordered{border:1px solid #dddddd;border-collapse:separate;*border-collapse:collapse;border-left:0;-webkit-border-radius:0px;-moz-border-radius:0px;border-radius:0px;}.table-bordered th,.table-bordered td{border-left:1px solid #dddddd;}
.table-bordered caption+thead tr:first-child th,.table-bordered caption+tbody tr:first-child th,.table-bordered caption+tbody tr:first-child td,.table-bordered colgroup+thead tr:first-child th,.table-bordered colgroup+tbody tr:first-child th,.table-bordered colgroup+tbody tr:first-child td,.table-bordered thead:first-child tr:first-child th,.table-bordered tbody:first-child tr:first-child th,.table-bordered tbody:first-child tr:first-child td{border-top:0;}
.table-bordered thead:first-child tr:first-child>th:first-child,.table-bordered tbody:first-child tr:first-child>td:first-child{-webkit-border-top-left-radius:0px;-moz-border-radius-topleft:0px;border-top-left-radius:0px;}
.table-bordered thead:first-child tr:first-child>th:last-child,.table-bordered tbody:first-child tr:first-child>td:last-child{-webkit-border-top-right-radius:0px;-moz-border-radius-topright:0px;border-top-right-radius:0px;}
.table-bordered thead:last-child tr:last-child>th:first-child,.table-bordered tbody:last-child tr:last-child>td:first-child,.table-bordered tfoot:last-child tr:last-child>td:first-child{-webkit-border-bottom-left-radius:0px;-moz-border-radius-bottomleft:0px;border-bottom-left-radius:0px;}
.table-bordered thead:last-child tr:last-child>th:last-child,.table-bordered tbody:last-child tr:last-child>td:last-child,.table-bordered tfoot:last-child tr:last-child>td:last-child{-webkit-border-bottom-right-radius:0px;-moz-border-radius-bottomright:0px;border-bottom-right-radius:0px;}
.table-bordered tfoot+tbody:last-child tr:last-child td:first-child{-webkit-border-bottom-left-radius:0;-moz-border-radius-bottomleft:0;border-bottom-left-radius:0;}
.table-bordered tfoot+tbody:last-child tr:last-child td:last-child{-webkit-border-bottom-right-radius:0;-moz-border-radius-bottomright:0;border-bottom-right-radius:0;}
.table-bordered caption+thead tr:first-child th:first-child,.table-bordered caption+tbody tr:first-child td:first-child,.table-bordered colgroup+thead tr:first-child th:first-child,.table-bordered colgroup+tbody tr:first-child td:first-child{-webkit-border-top-left-radius:0px;-moz-border-radius-topleft:0px;border-top-left-radius:0px;}
.table-bordered caption+thead tr:first-child th:last-child,.table-bordered caption+tbody tr:first-child td:last-child,.table-bordered colgroup+thead tr:first-child th:last-child,.table-bordered colgroup+tbody tr:first-child td:last-child{-webkit-border-top-right-radius:0px;-moz-border-radius-topright:0px;border-top-right-radius:0px;}
.table-striped tbody>tr:nth-child(odd)>td,.table-striped tbody>tr:nth-child(odd)>th{background-color:#f9f9f9;}
.table-hover tbody tr:hover td,.table-hover tbody tr:hover th{background-color:#e8f8fd;}
table td[class*="span"],table th[class*="span"],.row-fluid table td[class*="span"],.row-fluid table th[class*="span"]{display:table-cell;float:none;margin-left:0;}
.table td.span1,.table th.span1{float:none;width:44px;margin-left:0;}
.table td.span2,.table th.span2{float:none;width:124px;margin-left:0;}
.table td.span3,.table th.span3{float:none;width:204px;margin-left:0;}
.table td.span4,.table th.span4{float:none;width:284px;margin-left:0;}
.table td.span5,.table th.span5{float:none;width:364px;margin-left:0;}
.table td.span6,.table th.span6{float:none;width:444px;margin-left:0;}
.table td.span7,.table th.span7{float:none;width:524px;margin-left:0;}
.table td.span8,.table th.span8{float:none;width:604px;margin-left:0;}
.table td.span9,.table th.span9{float:none;width:684px;margin-left:0;}
.table td.span10,.table th.span10{float:none;width:764px;margin-left:0;}
.table td.span11,.table th.span11{float:none;width:844px;margin-left:0;}
.table td.span12,.table th.span12{float:none;width:924px;margin-left:0;}
.table tbody tr.success td{background-color:#3fb618;}
.table tbody tr.error td{background-color:#ff0039;}
.table tbody tr.warning td{background-color:#ff7518;}
.table tbody tr.info td{background-color:#9954bb;}
.table-hover tbody tr.success:hover td{background-color:#379f15;}
.table-hover tbody tr.error:hover td{background-color:#e60033;}
.table-hover tbody tr.warning:hover td{background-color:#fe6600;}
.table-hover tbody tr.info:hover td{background-color:#8d46b0;}
[class^="icon-"],[class*=" icon-"]{display:inline-block;width:14px;height:14px;*margin-right:.3em;line-height:14px;vertical-align:text-top;background-image:url("../img/glyphicons-halflings.png");background-position:14px 14px;background-repeat:no-repeat;margin-top:1px;}
.icon-white,.nav-pills>.active>a>[class^="icon-"],.nav-pills>.active>a>[class*=" icon-"],.nav-list>.active>a>[class^="icon-"],.nav-list>.active>a>[class*=" icon-"],.navbar-inverse .nav>.active>a>[class^="icon-"],.navbar-inverse .nav>.active>a>[class*=" icon-"],.dropdown-menu>li>a:hover>[class^="icon-"],.dropdown-menu>li>a:hover>[class*=" icon-"],.dropdown-menu>.active>a>[class^="icon-"],.dropdown-menu>.active>a>[class*=" icon-"],.dropdown-submenu:hover>a>[class^="icon-"],.dropdown-submenu:hover>a>[class*=" icon-"]{background-image:url("../img/glyphicons-halflings-white.png");}
.icon-glass{background-position:0 0;}
.icon-music{background-position:-24px 0;}
.icon-search{background-position:-48px 0;}
.icon-envelope{background-position:-72px 0;}
.icon-heart{background-position:-96px 0;}
.icon-star{background-position:-120px 0;}
.icon-star-empty{background-position:-144px 0;}
.icon-user{background-position:-168px 0;}
.icon-film{background-position:-192px 0;}
.icon-th-large{background-position:-216px 0;}
.icon-th{background-position:-240px 0;}
.icon-th-list{background-position:-264px 0;}
.icon-ok{background-position:-288px 0;}
.icon-remove{background-position:-312px 0;}
.icon-zoom-in{background-position:-336px 0;}
.icon-zoom-out{background-position:-360px 0;}
.icon-off{background-position:-384px 0;}
.icon-signal{background-position:-408px 0;}
.icon-cog{background-position:-432px 0;}
.icon-trash{background-position:-456px 0;}
.icon-home{background-position:0 -24px;}
.icon-file{background-position:-24px -24px;}
.icon-time{background-position:-48px -24px;}
.icon-road{background-position:-72px -24px;}
.icon-download-alt{background-position:-96px -24px;}
.icon-download{background-position:-120px -24px;}
.icon-upload{background-position:-144px -24px;}
.icon-inbox{background-position:-168px -24px;}
.icon-play-circle{background-position:-192px -24px;}
.icon-repeat{background-position:-216px -24px;}
.icon-refresh{background-position:-240px -24px;}
.icon-list-alt{background-position:-264px -24px;}
.icon-lock{background-position:-287px -24px;}
.icon-flag{background-position:-312px -24px;}
.icon-headphones{background-position:-336px -24px;}
.icon-volume-off{background-position:-360px -24px;}
.icon-volume-down{background-position:-384px -24px;}
.icon-volume-up{background-position:-408px -24px;}
.icon-qrcode{background-position:-432px -24px;}
.icon-barcode{background-position:-456px -24px;}
.icon-tag{background-position:0 -48px;}
.icon-tags{background-position:-25px -48px;}
.icon-book{background-position:-48px -48px;}
.icon-bookmark{background-position:-72px -48px;}
.icon-print{background-position:-96px -48px;}
.icon-camera{background-position:-120px -48px;}
.icon-font{background-position:-144px -48px;}
.icon-bold{background-position:-167px -48px;}
.icon-italic{background-position:-192px -48px;}
.icon-text-height{background-position:-216px -48px;}
.icon-text-width{background-position:-240px -48px;}
.icon-align-left{background-position:-264px -48px;}
.icon-align-center{background-position:-288px -48px;}
.icon-align-right{background-position:-312px -48px;}
.icon-align-justify{background-position:-336px -48px;}
.icon-list{background-position:-360px -48px;}
.icon-indent-left{background-position:-384px -48px;}
.icon-indent-right{background-position:-408px -48px;}
.icon-facetime-video{background-position:-432px -48px;}
.icon-picture{background-position:-456px -48px;}
.icon-pencil{background-position:0 -72px;}
.icon-map-marker{background-position:-24px -72px;}
.icon-adjust{background-position:-48px -72px;}
.icon-tint{background-position:-72px -72px;}
.icon-edit{background-position:-96px -72px;}
.icon-share{background-position:-120px -72px;}
.icon-check{background-position:-144px -72px;}
.icon-move{background-position:-168px -72px;}
.icon-step-backward{background-position:-192px -72px;}
.icon-fast-backward{background-position:-216px -72px;}
.icon-backward{background-position:-240px -72px;}
.icon-play{background-position:-264px -72px;}
.icon-pause{background-position:-288px -72px;}
.icon-stop{background-position:-312px -72px;}
.icon-forward{background-position:-336px -72px;}
.icon-fast-forward{background-position:-360px -72px;}
.icon-step-forward{background-position:-384px -72px;}
.icon-eject{background-position:-408px -72px;}
.icon-chevron-left{background-position:-432px -72px;}
.icon-chevron-right{background-position:-456px -72px;}
.icon-plus-sign{background-position:0 -96px;}
.icon-minus-sign{background-position:-24px -96px;}
.icon-remove-sign{background-position:-48px -96px;}
.icon-ok-sign{background-position:-72px -96px;}
.icon-question-sign{background-position:-96px -96px;}
.icon-info-sign{background-position:-120px -96px;}
.icon-screenshot{background-position:-144px -96px;}
.icon-remove-circle{background-position:-168px -96px;}
.icon-ok-circle{background-position:-192px -96px;}
.icon-ban-circle{background-position:-216px -96px;}
.icon-arrow-left{background-position:-240px -96px;}
.icon-arrow-right{background-position:-264px -96px;}
.icon-arrow-up{background-position:-289px -96px;}
.icon-arrow-down{background-position:-312px -96px;}
.icon-share-alt{background-position:-336px -96px;}
.icon-resize-full{background-position:-360px -96px;}
.icon-resize-small{background-position:-384px -96px;}
.icon-plus{background-position:-408px -96px;}
.icon-minus{background-position:-433px -96px;}
.icon-asterisk{background-position:-456px -96px;}
.icon-exclamation-sign{background-position:0 -120px;}
.icon-gift{background-position:-24px -120px;}
.icon-leaf{background-position:-48px -120px;}
.icon-fire{background-position:-72px -120px;}
.icon-eye-open{background-position:-96px -120px;}
.icon-eye-close{background-position:-120px -120px;}
.icon-warning-sign{background-position:-144px -120px;}
.icon-plane{background-position:-168px -120px;}
.icon-calendar{background-position:-192px -120px;}
.icon-random{background-position:-216px -120px;width:16px;}
.icon-comment{background-position:-240px -120px;}
.icon-magnet{background-position:-264px -120px;}
.icon-chevron-up{background-position:-288px -120px;}
.icon-chevron-down{background-position:-313px -119px;}
.icon-retweet{background-position:-336px -120px;}
.icon-shopping-cart{background-position:-360px -120px;}
.icon-folder-close{background-position:-384px -120px;}
.icon-folder-open{background-position:-408px -120px;width:16px;}
.icon-resize-vertical{background-position:-432px -119px;}
.icon-resize-horizontal{background-position:-456px -118px;}
.icon-hdd{background-position:0 -144px;}
.icon-bullhorn{background-position:-24px -144px;}
.icon-bell{background-position:-48px -144px;}
.icon-certificate{background-position:-72px -144px;}
.icon-thumbs-up{background-position:-96px -144px;}
.icon-thumbs-down{background-position:-120px -144px;}
.icon-hand-right{background-position:-144px -144px;}
.icon-hand-left{background-position:-168px -144px;}
.icon-hand-up{background-position:-192px -144px;}
.icon-hand-down{background-position:-216px -144px;}
.icon-circle-arrow-right{background-position:-240px -144px;}
.icon-circle-arrow-left{background-position:-264px -144px;}
.icon-circle-arrow-up{background-position:-288px -144px;}
.icon-circle-arrow-down{background-position:-312px -144px;}
.icon-globe{background-position:-336px -144px;}
.icon-wrench{background-position:-360px -144px;}
.icon-tasks{background-position:-384px -144px;}
.icon-filter{background-position:-408px -144px;}
.icon-briefcase{background-position:-432px -144px;}
.icon-fullscreen{background-position:-456px -144px;}
.dropup,.dropdown{position:relative;}
.dropdown-toggle{*margin-bottom:-3px;}
.dropdown-toggle:active,.open .dropdown-toggle{outline:0;}
.caret{display:inline-block;width:0;height:0;vertical-align:top;border-top:4px solid #000000;border-right:4px solid transparent;border-left:4px solid transparent;content:"";}
.dropdown .caret{margin-top:8px;margin-left:2px;}
.dropdown-menu{position:absolute;top:100%;left:0;z-index:1000;display:none;float:left;min-width:160px;padding:5px 0;margin:2px 0 0;list-style:none;background-color:#ffffff;border:1px solid #ccc;border:1px solid rgba(0, 0, 0, 0.2);*border-right-width:2px;*border-bottom-width:2px;-webkit-border-radius:6px;-moz-border-radius:6px;border-radius:6px;-webkit-box-shadow:0 5px 10px rgba(0, 0, 0, 0.2);-moz-box-shadow:0 5px 10px rgba(0, 0, 0, 0.2);box-shadow:0 5px 10px rgba(0, 0, 0, 0.2);-webkit-background-clip:padding-box;-moz-background-clip:padding;background-clip:padding-box;}.dropdown-menu.pull-right{right:0;left:auto;}
.dropdown-menu .divider{*width:100%;height:1px;margin:9px 1px;*margin:-5px 0 5px;overflow:hidden;background-color:#e5e5e5;border-bottom:1px solid #ffffff;}
.dropdown-menu li>a{display:block;padding:3px 20px;clear:both;font-weight:normal;line-height:20px;color:#999999;white-space:nowrap;}
.dropdown-menu li>a:hover,.dropdown-menu li>a:focus,.dropdown-submenu:hover>a{text-decoration:none;color:#ffffff;background-color:#007af5;background-image:-moz-linear-gradient(top, #007fff, #0072e6);background-image:-webkit-gradient(linear, 0 0, 0 100%, from(#007fff), to(#0072e6));background-image:-webkit-linear-gradient(top, #007fff, #0072e6);background-image:-o-linear-gradient(top, #007fff, #0072e6);background-image:linear-gradient(to bottom, #007fff, #0072e6);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff007fff', endColorstr='#ff0072e6', GradientType=0);}
.dropdown-menu .active>a,.dropdown-menu .active>a:hover{color:#ffffff;text-decoration:none;outline:0;background-color:#007af5;background-image:-moz-linear-gradient(top, #007fff, #0072e6);background-image:-webkit-gradient(linear, 0 0, 0 100%, from(#007fff), to(#0072e6));background-image:-webkit-linear-gradient(top, #007fff, #0072e6);background-image:-o-linear-gradient(top, #007fff, #0072e6);background-image:linear-gradient(to bottom, #007fff, #0072e6);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff007fff', endColorstr='#ff0072e6', GradientType=0);}
.dropdown-menu .disabled>a,.dropdown-menu .disabled>a:hover{color:#dfdfdf;}
.dropdown-menu .disabled>a:hover{text-decoration:none;background-color:transparent;background-image:none;filter:progid:DXImageTransform.Microsoft.gradient(enabled = false);cursor:default;}
.open{*z-index:1000;}.open >.dropdown-menu{display:block;}
.pull-right>.dropdown-menu{right:0;left:auto;}
.dropup .caret,.navbar-fixed-bottom .dropdown .caret{border-top:0;border-bottom:4px solid #000000;content:"";}
.dropup .dropdown-menu,.navbar-fixed-bottom .dropdown .dropdown-menu{top:auto;bottom:100%;margin-bottom:1px;}
.dropdown-submenu{position:relative;}
.dropdown-submenu>.dropdown-menu{top:0;left:100%;margin-top:-6px;margin-left:-1px;-webkit-border-radius:0 6px 6px 6px;-moz-border-radius:0 6px 6px 6px;border-radius:0 6px 6px 6px;}
.dropdown-submenu:hover>.dropdown-menu{display:block;}
.dropup .dropdown-submenu>.dropdown-menu{top:auto;bottom:0;margin-top:0;margin-bottom:-2px;-webkit-border-radius:5px 5px 5px 0;-moz-border-radius:5px 5px 5px 0;border-radius:5px 5px 5px 0;}
.dropdown-submenu>a:after{display:block;content:" ";float:right;width:0;height:0;border-color:transparent;border-style:solid;border-width:5px 0 5px 5px;border-left-color:#cccccc;margin-top:5px;margin-right:-10px;}
.dropdown-submenu:hover>a:after{border-left-color:#ffffff;}
.dropdown-submenu.pull-left{float:none;}.dropdown-submenu.pull-left>.dropdown-menu{left:-100%;margin-left:10px;-webkit-border-radius:6px 0 6px 6px;-moz-border-radius:6px 0 6px 6px;border-radius:6px 0 6px 6px;}
.dropdown .dropdown-menu .nav-header{padding-left:20px;padding-right:20px;}
.typeahead{z-index:1051;margin-top:2px;-webkit-border-radius:0px;-moz-border-radius:0px;border-radius:0px;}
.well{min-height:20px;padding:19px;margin-bottom:20px;background-color:#eeeeee;border:1px solid #dcdcdc;-webkit-border-radius:0px;-moz-border-radius:0px;border-radius:0px;-webkit-box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.05);-moz-box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.05);box-shadow:inset 0 1px 1px rgba(0, 0, 0, 0.05);}.well blockquote{border-color:#ddd;border-color:rgba(0, 0, 0, 0.15);}
.well-large{padding:24px;-webkit-border-radius:0px;-moz-border-radius:0px;border-radius:0px;}
.well-small{padding:9px;-webkit-border-radius:0px;-moz-border-radius:0px;border-radius:0px;}
.fade{opacity:0;-webkit-transition:opacity 0.15s linear;-moz-transition:opacity 0.15s linear;-o-transition:opacity 0.15s linear;transition:opacity 0.15s linear;}.fade.in{opacity:1;}
.collapse{position:relative;height:0;overflow:hidden;-webkit-transition:height 0.35s ease;-moz-transition:height 0.35s ease;-o-transition:height 0.35s ease;transition:height 0.35s ease;}.collapse.in{height:auto;}
.close{float:right;font-size:20px;font-weight:bold;line-height:20px;color:#000000;text-shadow:0 1px 0 #ffffff;opacity:0.2;filter:alpha(opacity=20);}.close:hover{color:#000000;text-decoration:none;cursor:pointer;opacity:0.4;filter:alpha(opacity=40);}
button.close{padding:0;cursor:pointer;background:transparent;border:0;-webkit-appearance:none;}
.btn{display:inline-block;*display:inline;*zoom:1;padding:4px 12px;margin-bottom:0;font-size:14px;line-height:20px;text-align:center;vertical-align:middle;cursor:pointer;color:#999999;text-shadow:0 1px 1px rgba(255, 255, 255, 0.75);background-color:#dfdfdf;background-image:-moz-linear-gradient(top, #eeeeee, #c8c8c8);background-image:-webkit-gradient(linear, 0 0, 0 100%, from(#eeeeee), to(#c8c8c8));background-image:-webkit-linear-gradient(top, #eeeeee, #c8c8c8);background-image:-o-linear-gradient(top, #eeeeee, #c8c8c8);background-image:linear-gradient(to bottom, #eeeeee, #c8c8c8);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffeeeeee', endColorstr='#ffc8c8c8', GradientType=0);border-color:#c8c8c8 #c8c8c8 #a2a2a2;border-color:rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);*background-color:#c8c8c8;filter:progid:DXImageTransform.Microsoft.gradient(enabled = false);border:1px solid #bbbbbb;*border:0;border-bottom-color:#a2a2a2;-webkit-border-radius:0px;-moz-border-radius:0px;border-radius:0px;*margin-left:.3em;-webkit-box-shadow:inset 0 1px 0 rgba(255,255,255,.2), 0 1px 2px rgba(0,0,0,.05);-moz-box-shadow:inset 0 1px 0 rgba(255,255,255,.2), 0 1px 2px rgba(0,0,0,.05);box-shadow:inset 0 1px 0 rgba(255,255,255,.2), 0 1px 2px rgba(0,0,0,.05);}.btn:hover,.btn:active,.btn.active,.btn.disabled,.btn[disabled]{color:#999999;background-color:#c8c8c8;*background-color:#bbbbbb;}
.btn:active,.btn.active{background-color:#aeaeae \9;}
.btn:first-child{*margin-left:0;}
.btn:hover{color:#999999;text-decoration:none;background-position:0 -15px;-webkit-transition:background-position 0.1s linear;-moz-transition:background-position 0.1s linear;-o-transition:background-position 0.1s linear;transition:background-position 0.1s linear;}
.btn:focus{outline:thin dotted #333;outline:5px auto -webkit-focus-ring-color;outline-offset:-2px;}
.btn.active,.btn:active{background-image:none;outline:0;-webkit-box-shadow:inset 0 2px 4px rgba(0,0,0,.15), 0 1px 2px rgba(0,0,0,.05);-moz-box-shadow:inset 0 2px 4px rgba(0,0,0,.15), 0 1px 2px rgba(0,0,0,.05);box-shadow:inset 0 2px 4px rgba(0,0,0,.15), 0 1px 2px rgba(0,0,0,.05);}
.btn.disabled,.btn[disabled]{cursor:default;background-image:none;opacity:0.65;filter:alpha(opacity=65);-webkit-box-shadow:none;-moz-box-shadow:none;box-shadow:none;}
.btn-large{padding:22px 30px;font-size:17.5px;-webkit-border-radius:0px;-moz-border-radius:0px;border-radius:0px;}
.btn-large [class^="icon-"],.btn-large [class*=" icon-"]{margin-top:4px;}
.btn-small{padding:2px 10px;font-size:11.9px;-webkit-border-radius:0px;-moz-border-radius:0px;border-radius:0px;}
.btn-small [class^="icon-"],.btn-small [class*=" icon-"]{margin-top:0;}
.btn-mini [class^="icon-"],.btn-mini [class*=" icon-"]{margin-top:-1px;}
.btn-mini{padding:2px 6px;font-size:10.5px;-webkit-border-radius:0px;-moz-border-radius:0px;border-radius:0px;}
.btn-block{display:block;width:100%;padding-left:0;padding-right:0;-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box;}
.btn-block+.btn-block{margin-top:5px;}
input[type="submit"].btn-block,input[type="reset"].btn-block,input[type="button"].btn-block{width:100%;}
.btn-primary.active,.btn-warning.active,.btn-danger.active,.btn-success.active,.btn-info.active,.btn-inverse.active{color:rgba(255, 255, 255, 0.75);}
.btn{border-color:#c5c5c5;border-color:rgba(0, 0, 0, 0.15) rgba(0, 0, 0, 0.15) rgba(0, 0, 0, 0.25);}
.btn-primary{color:#ffffff;text-shadow:0 -1px 0 rgba(0, 0, 0, 0.25);background-color:#0f82f5;background-image:-moz-linear-gradient(top, #1a8cff, #0072e6);background-image:-webkit-gradient(linear, 0 0, 0 100%, from(#1a8cff), to(#0072e6));background-image:-webkit-linear-gradient(top, #1a8cff, #0072e6);background-image:-o-linear-gradient(top, #1a8cff, #0072e6);background-image:linear-gradient(to bottom, #1a8cff, #0072e6);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff1a8cff', endColorstr='#ff0072e6', GradientType=0);border-color:#0072e6 #0072e6 #004c99;border-color:rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);*background-color:#0072e6;filter:progid:DXImageTransform.Microsoft.gradient(enabled = false);}.btn-primary:hover,.btn-primary:active,.btn-primary.active,.btn-primary.disabled,.btn-primary[disabled]{color:#ffffff;background-color:#0072e6;*background-color:#0066cc;}
.btn-primary:active,.btn-primary.active{background-color:#0059b3 \9;}
.btn-warning{color:#ffffff;text-shadow:0 -1px 0 rgba(0, 0, 0, 0.25);background-color:#fe781e;background-image:-moz-linear-gradient(top, #ff8432, #fe6600);background-image:-webkit-gradient(linear, 0 0, 0 100%, from(#ff8432), to(#fe6600));background-image:-webkit-linear-gradient(top, #ff8432, #fe6600);background-image:-o-linear-gradient(top, #ff8432, #fe6600);background-image:linear-gradient(to bottom, #ff8432, #fe6600);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffff8432', endColorstr='#fffe6600', GradientType=0);border-color:#fe6600 #fe6600 #b14700;border-color:rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);*background-color:#fe6600;filter:progid:DXImageTransform.Microsoft.gradient(enabled = false);}.btn-warning:hover,.btn-warning:active,.btn-warning.active,.btn-warning.disabled,.btn-warning[disabled]{color:#ffffff;background-color:#fe6600;*background-color:#e45c00;}
.btn-warning:active,.btn-warning.active{background-color:#cb5200 \9;}
.btn-danger{color:#ffffff;text-shadow:0 -1px 0 rgba(0, 0, 0, 0.25);background-color:#f50f43;background-image:-moz-linear-gradient(top, #ff1a4d, #e60033);background-image:-webkit-gradient(linear, 0 0, 0 100%, from(#ff1a4d), to(#e60033));background-image:-webkit-linear-gradient(top, #ff1a4d, #e60033);background-image:-o-linear-gradient(top, #ff1a4d, #e60033);background-image:linear-gradient(to bottom, #ff1a4d, #e60033);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffff1a4d', endColorstr='#ffe60033', GradientType=0);border-color:#e60033 #e60033 #990022;border-color:rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);*background-color:#e60033;filter:progid:DXImageTransform.Microsoft.gradient(enabled = false);}.btn-danger:hover,.btn-danger:active,.btn-danger.active,.btn-danger.disabled,.btn-danger[disabled]{color:#ffffff;background-color:#e60033;*background-color:#cc002e;}
.btn-danger:active,.btn-danger.active{background-color:#b30028 \9;}
.btn-success{color:#ffffff;text-shadow:0 -1px 0 rgba(0, 0, 0, 0.25);background-color:#41bb19;background-image:-moz-linear-gradient(top, #47cd1b, #379f15);background-image:-webkit-gradient(linear, 0 0, 0 100%, from(#47cd1b), to(#379f15));background-image:-webkit-linear-gradient(top, #47cd1b, #379f15);background-image:-o-linear-gradient(top, #47cd1b, #379f15);background-image:linear-gradient(to bottom, #47cd1b, #379f15);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff47cd1b', endColorstr='#ff379f15', GradientType=0);border-color:#379f15 #379f15 #205c0c;border-color:rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);*background-color:#379f15;filter:progid:DXImageTransform.Microsoft.gradient(enabled = false);}.btn-success:hover,.btn-success:active,.btn-success.active,.btn-success.disabled,.btn-success[disabled]{color:#ffffff;background-color:#379f15;*background-color:#2f8912;}
.btn-success:active,.btn-success.active{background-color:#28720f \9;}
.btn-info{color:#ffffff;text-shadow:0 -1px 0 rgba(0, 0, 0, 0.25);background-color:#9b59bb;background-image:-moz-linear-gradient(top, #a466c2, #8d46b0);background-image:-webkit-gradient(linear, 0 0, 0 100%, from(#a466c2), to(#8d46b0));background-image:-webkit-linear-gradient(top, #a466c2, #8d46b0);background-image:-o-linear-gradient(top, #a466c2, #8d46b0);background-image:linear-gradient(to bottom, #a466c2, #8d46b0);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffa466c2', endColorstr='#ff8d46b0', GradientType=0);border-color:#8d46b0 #8d46b0 #613079;border-color:rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);*background-color:#8d46b0;filter:progid:DXImageTransform.Microsoft.gradient(enabled = false);}.btn-info:hover,.btn-info:active,.btn-info.active,.btn-info.disabled,.btn-info[disabled]{color:#ffffff;background-color:#8d46b0;*background-color:#7e3f9d;}
.btn-info:active,.btn-info.active{background-color:#6f378b \9;}
.btn-inverse{color:#ffffff;text-shadow:0 -1px 0 rgba(0, 0, 0, 0.25);background-color:#080808;background-image:-moz-linear-gradient(top, #0d0d0d, #000000);background-image:-webkit-gradient(linear, 0 0, 0 100%, from(#0d0d0d), to(#000000));background-image:-webkit-linear-gradient(top, #0d0d0d, #000000);background-image:-o-linear-gradient(top, #0d0d0d, #000000);background-image:linear-gradient(to bottom, #0d0d0d, #000000);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff0d0d0d', endColorstr='#ff000000', GradientType=0);border-color:#000000 #000000 #000000;border-color:rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);*background-color:#000000;filter:progid:DXImageTransform.Microsoft.gradient(enabled = false);}.btn-inverse:hover,.btn-inverse:active,.btn-inverse.active,.btn-inverse.disabled,.btn-inverse[disabled]{color:#ffffff;background-color:#000000;*background-color:#000000;}
.btn-inverse:active,.btn-inverse.active{background-color:#000000 \9;}
button.btn,input[type="submit"].btn{*padding-top:3px;*padding-bottom:3px;}button.btn::-moz-focus-inner,input[type="submit"].btn::-moz-focus-inner{padding:0;border:0;}
button.btn.btn-large,input[type="submit"].btn.btn-large{*padding-top:7px;*padding-bottom:7px;}
button.btn.btn-small,input[type="submit"].btn.btn-small{*padding-top:3px;*padding-bottom:3px;}
button.btn.btn-mini,input[type="submit"].btn.btn-mini{*padding-top:1px;*padding-bottom:1px;}
.btn-link,.btn-link:active,.btn-link[disabled]{background-color:transparent;background-image:none;-webkit-box-shadow:none;-moz-box-shadow:none;box-shadow:none;}
.btn-link{border-color:transparent;cursor:pointer;color:#007fff;-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;}
.btn-link:hover{color:#0066cc;text-decoration:underline;background-color:transparent;}
.btn-link[disabled]:hover{color:#999999;text-decoration:none;}
.btn-group{position:relative;display:inline-block;*display:inline;*zoom:1;font-size:0;vertical-align:middle;white-space:nowrap;*margin-left:.3em;}.btn-group:first-child{*margin-left:0;}
.btn-group+.btn-group{margin-left:5px;}
.btn-toolbar{font-size:0;margin-top:10px;margin-bottom:10px;}.btn-toolbar>.btn+.btn,.btn-toolbar>.btn-group+.btn,.btn-toolbar>.btn+.btn-group{margin-left:5px;}
.btn-group>.btn{position:relative;-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;}
.btn-group>.btn+.btn{margin-left:-1px;}
.btn-group>.btn,.btn-group>.dropdown-menu,.btn-group>.popover{font-size:14px;}
.btn-group>.btn-mini{font-size:10.5px;}
.btn-group>.btn-small{font-size:11.9px;}
.btn-group>.btn-large{font-size:17.5px;}
.btn-group>.btn:first-child{margin-left:0;-webkit-border-top-left-radius:0px;-moz-border-radius-topleft:0px;border-top-left-radius:0px;-webkit-border-bottom-left-radius:0px;-moz-border-radius-bottomleft:0px;border-bottom-left-radius:0px;}
.btn-group>.btn:last-child,.btn-group>.dropdown-toggle{-webkit-border-top-right-radius:0px;-moz-border-radius-topright:0px;border-top-right-radius:0px;-webkit-border-bottom-right-radius:0px;-moz-border-radius-bottomright:0px;border-bottom-right-radius:0px;}
.btn-group>.btn.large:first-child{margin-left:0;-webkit-border-top-left-radius:0px;-moz-border-radius-topleft:0px;border-top-left-radius:0px;-webkit-border-bottom-left-radius:0px;-moz-border-radius-bottomleft:0px;border-bottom-left-radius:0px;}
.btn-group>.btn.large:last-child,.btn-group>.large.dropdown-toggle{-webkit-border-top-right-radius:0px;-moz-border-radius-topright:0px;border-top-right-radius:0px;-webkit-border-bottom-right-radius:0px;-moz-border-radius-bottomright:0px;border-bottom-right-radius:0px;}
.btn-group>.btn:hover,.btn-group>.btn:focus,.btn-group>.btn:active,.btn-group>.btn.active{z-index:2;}
.btn-group .dropdown-toggle:active,.btn-group.open .dropdown-toggle{outline:0;}
.btn-group>.btn+.dropdown-toggle{padding-left:8px;padding-right:8px;-webkit-box-shadow:inset 1px 0 0 rgba(255,255,255,.125), inset 0 1px 0 rgba(255,255,255,.2), 0 1px 2px rgba(0,0,0,.05);-moz-box-shadow:inset 1px 0 0 rgba(255,255,255,.125), inset 0 1px 0 rgba(255,255,255,.2), 0 1px 2px rgba(0,0,0,.05);box-shadow:inset 1px 0 0 rgba(255,255,255,.125), inset 0 1px 0 rgba(255,255,255,.2), 0 1px 2px rgba(0,0,0,.05);*padding-top:5px;*padding-bottom:5px;}
.btn-group>.btn-mini+.dropdown-toggle{padding-left:5px;padding-right:5px;*padding-top:2px;*padding-bottom:2px;}
.btn-group>.btn-small+.dropdown-toggle{*padding-top:5px;*padding-bottom:4px;}
.btn-group>.btn-large+.dropdown-toggle{padding-left:12px;padding-right:12px;*padding-top:7px;*padding-bottom:7px;}
.btn-group.open .dropdown-toggle{background-image:none;-webkit-box-shadow:inset 0 2px 4px rgba(0,0,0,.15), 0 1px 2px rgba(0,0,0,.05);-moz-box-shadow:inset 0 2px 4px rgba(0,0,0,.15), 0 1px 2px rgba(0,0,0,.05);box-shadow:inset 0 2px 4px rgba(0,0,0,.15), 0 1px 2px rgba(0,0,0,.05);}
.btn-group.open .btn.dropdown-toggle{background-color:#c8c8c8;}
.btn-group.open .btn-primary.dropdown-toggle{background-color:#0072e6;}
.btn-group.open .btn-warning.dropdown-toggle{background-color:#fe6600;}
.btn-group.open .btn-danger.dropdown-toggle{background-color:#e60033;}
.btn-group.open .btn-success.dropdown-toggle{background-color:#379f15;}
.btn-group.open .btn-info.dropdown-toggle{background-color:#8d46b0;}
.btn-group.open .btn-inverse.dropdown-toggle{background-color:#000000;}
.btn .caret{margin-top:8px;margin-left:0;}
.btn-mini .caret,.btn-small .caret,.btn-large .caret{margin-top:6px;}
.btn-large .caret{border-left-width:5px;border-right-width:5px;border-top-width:5px;}
.dropup .btn-large .caret{border-bottom-width:5px;}
.btn-primary .caret,.btn-warning .caret,.btn-danger .caret,.btn-info .caret,.btn-success .caret,.btn-inverse .caret{border-top-color:#ffffff;border-bottom-color:#ffffff;}
.btn-group-vertical{display:inline-block;*display:inline;*zoom:1;}
.btn-group-vertical>.btn{display:block;float:none;max-width:100%;-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;}
.btn-group-vertical>.btn+.btn{margin-left:0;margin-top:-1px;}
.btn-group-vertical>.btn:first-child{-webkit-border-radius:0px 0px 0 0;-moz-border-radius:0px 0px 0 0;border-radius:0px 0px 0 0;}
.btn-group-vertical>.btn:last-child{-webkit-border-radius:0 0 0px 0px;-moz-border-radius:0 0 0px 0px;border-radius:0 0 0px 0px;}
.btn-group-vertical>.btn-large:first-child{-webkit-border-radius:0px 0px 0 0;-moz-border-radius:0px 0px 0 0;border-radius:0px 0px 0 0;}
.btn-group-vertical>.btn-large:last-child{-webkit-border-radius:0 0 0px 0px;-moz-border-radius:0 0 0px 0px;border-radius:0 0 0px 0px;}
.alert{padding:8px 35px 8px 14px;margin-bottom:20px;text-shadow:0 1px 0 rgba(255, 255, 255, 0.5);background-color:#ff7518;border:1px solid transparent;-webkit-border-radius:0px;-moz-border-radius:0px;border-radius:0px;}
.alert,.alert h4{color:#ffffff;}
.alert h4{margin:0;}
.alert .close{position:relative;top:-2px;right:-21px;line-height:20px;}
.alert-success{background-color:#3fb618;border-color:transparent;color:#ffffff;}
.alert-success h4{color:#ffffff;}
.alert-danger,.alert-error{background-color:#ff0039;border-color:transparent;color:#ffffff;}
.alert-danger h4,.alert-error h4{color:#ffffff;}
.alert-info{background-color:#9954bb;border-color:transparent;color:#ffffff;}
.alert-info h4{color:#ffffff;}
.alert-block{padding-top:14px;padding-bottom:14px;}
.alert-block>p,.alert-block>ul{margin-bottom:0;}
.alert-block p+p{margin-top:5px;}
.nav{margin-left:0;margin-bottom:20px;list-style:none;}
.nav>li>a{display:block;}
.nav>li>a:hover{text-decoration:none;background-color:#eeeeee;}
.nav>li>a>img{max-width:none;}
.nav>.pull-right{float:right;}
.nav-header{display:block;padding:3px 15px;font-size:11px;font-weight:bold;line-height:20px;color:#dfdfdf;text-shadow:0 1px 0 rgba(255, 255, 255, 0.5);text-transform:uppercase;}
.nav li+.nav-header{margin-top:9px;}
.nav-list{padding-left:15px;padding-right:15px;margin-bottom:0;}
.nav-list>li>a,.nav-list .nav-header{margin-left:-15px;margin-right:-15px;text-shadow:0 1px 0 rgba(255, 255, 255, 0.5);}
.nav-list>li>a{padding:3px 15px;}
.nav-list>.active>a,.nav-list>.active>a:hover{color:#ffffff;text-shadow:0 -1px 0 rgba(0, 0, 0, 0.2);background-color:#007fff;}
.nav-list [class^="icon-"],.nav-list [class*=" icon-"]{margin-right:2px;}
.nav-list .divider{*width:100%;height:1px;margin:9px 1px;*margin:-5px 0 5px;overflow:hidden;background-color:#e5e5e5;border-bottom:1px solid #ffffff;}
.nav-tabs,.nav-pills{*zoom:1;}.nav-tabs:before,.nav-pills:before,.nav-tabs:after,.nav-pills:after{display:table;content:"";line-height:0;}
.nav-tabs:after,.nav-pills:after{clear:both;}
.nav-tabs>li,.nav-pills>li{float:left;}
.nav-tabs>li>a,.nav-pills>li>a{padding-right:12px;padding-left:12px;margin-right:2px;line-height:14px;}
.nav-tabs{border-bottom:1px solid #ddd;}
.nav-tabs>li{margin-bottom:-1px;}
.nav-tabs>li>a{padding-top:8px;padding-bottom:8px;line-height:20px;border:1px solid transparent;-webkit-border-radius:4px 4px 0 0;-moz-border-radius:4px 4px 0 0;border-radius:4px 4px 0 0;}.nav-tabs>li>a:hover{border-color:#eeeeee #eeeeee #dddddd;}
.nav-tabs>.active>a,.nav-tabs>.active>a:hover{color:#bbbbbb;background-color:#ffffff;border:1px solid #ddd;border-bottom-color:transparent;cursor:default;}
.nav-pills>li>a{padding-top:8px;padding-bottom:8px;margin-top:2px;margin-bottom:2px;-webkit-border-radius:5px;-moz-border-radius:5px;border-radius:5px;}
.nav-pills>.active>a,.nav-pills>.active>a:hover{color:#ffffff;background-color:#007fff;}
.nav-stacked>li{float:none;}
.nav-stacked>li>a{margin-right:0;}
.nav-tabs.nav-stacked{border-bottom:0;}
.nav-tabs.nav-stacked>li>a{border:1px solid #ddd;-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;}
.nav-tabs.nav-stacked>li:first-child>a{-webkit-border-top-right-radius:4px;-moz-border-radius-topright:4px;border-top-right-radius:4px;-webkit-border-top-left-radius:4px;-moz-border-radius-topleft:4px;border-top-left-radius:4px;}
.nav-tabs.nav-stacked>li:last-child>a{-webkit-border-bottom-right-radius:4px;-moz-border-radius-bottomright:4px;border-bottom-right-radius:4px;-webkit-border-bottom-left-radius:4px;-moz-border-radius-bottomleft:4px;border-bottom-left-radius:4px;}
.nav-tabs.nav-stacked>li>a:hover{border-color:#ddd;z-index:2;}
.nav-pills.nav-stacked>li>a{margin-bottom:3px;}
.nav-pills.nav-stacked>li:last-child>a{margin-bottom:1px;}
.nav-tabs .dropdown-menu{-webkit-border-radius:0 0 6px 6px;-moz-border-radius:0 0 6px 6px;border-radius:0 0 6px 6px;}
.nav-pills .dropdown-menu{-webkit-border-radius:6px;-moz-border-radius:6px;border-radius:6px;}
.nav .dropdown-toggle .caret{border-top-color:#007fff;border-bottom-color:#007fff;margin-top:6px;}
.nav .dropdown-toggle:hover .caret{border-top-color:#0066cc;border-bottom-color:#0066cc;}
.nav-tabs .dropdown-toggle .caret{margin-top:8px;}
.nav .active .dropdown-toggle .caret{border-top-color:#fff;border-bottom-color:#fff;}
.nav-tabs .active .dropdown-toggle .caret{border-top-color:#bbbbbb;border-bottom-color:#bbbbbb;}
.nav>.dropdown.active>a:hover{cursor:pointer;}
.nav-tabs .open .dropdown-toggle,.nav-pills .open .dropdown-toggle,.nav>li.dropdown.open.active>a:hover{color:#ffffff;background-color:#dfdfdf;border-color:#dfdfdf;}
.nav li.dropdown.open .caret,.nav li.dropdown.open.active .caret,.nav li.dropdown.open a:hover .caret{border-top-color:#ffffff;border-bottom-color:#ffffff;opacity:1;filter:alpha(opacity=100);}
.tabs-stacked .open>a:hover{border-color:#dfdfdf;}
.tabbable{*zoom:1;}.tabbable:before,.tabbable:after{display:table;content:"";line-height:0;}
.tabbable:after{clear:both;}
.tab-content{overflow:auto;}
.tabs-below>.nav-tabs,.tabs-right>.nav-tabs,.tabs-left>.nav-tabs{border-bottom:0;}
.tab-content>.tab-pane,.pill-content>.pill-pane{display:none;}
.tab-content>.active,.pill-content>.active{display:block;}
.tabs-below>.nav-tabs{border-top:1px solid #ddd;}
.tabs-below>.nav-tabs>li{margin-top:-1px;margin-bottom:0;}
.tabs-below>.nav-tabs>li>a{-webkit-border-radius:0 0 4px 4px;-moz-border-radius:0 0 4px 4px;border-radius:0 0 4px 4px;}.tabs-below>.nav-tabs>li>a:hover{border-bottom-color:transparent;border-top-color:#ddd;}
.tabs-below>.nav-tabs>.active>a,.tabs-below>.nav-tabs>.active>a:hover{border-color:transparent #ddd #ddd #ddd;}
.tabs-left>.nav-tabs>li,.tabs-right>.nav-tabs>li{float:none;}
.tabs-left>.nav-tabs>li>a,.tabs-right>.nav-tabs>li>a{min-width:74px;margin-right:0;margin-bottom:3px;}
.tabs-left>.nav-tabs{float:left;margin-right:19px;border-right:1px solid #ddd;}
.tabs-left>.nav-tabs>li>a{margin-right:-1px;-webkit-border-radius:4px 0 0 4px;-moz-border-radius:4px 0 0 4px;border-radius:4px 0 0 4px;}
.tabs-left>.nav-tabs>li>a:hover{border-color:#eeeeee #dddddd #eeeeee #eeeeee;}
.tabs-left>.nav-tabs .active>a,.tabs-left>.nav-tabs .active>a:hover{border-color:#ddd transparent #ddd #ddd;*border-right-color:#ffffff;}
.tabs-right>.nav-tabs{float:right;margin-left:19px;border-left:1px solid #ddd;}
.tabs-right>.nav-tabs>li>a{margin-left:-1px;-webkit-border-radius:0 4px 4px 0;-moz-border-radius:0 4px 4px 0;border-radius:0 4px 4px 0;}
.tabs-right>.nav-tabs>li>a:hover{border-color:#eeeeee #eeeeee #eeeeee #dddddd;}
.tabs-right>.nav-tabs .active>a,.tabs-right>.nav-tabs .active>a:hover{border-color:#ddd #ddd #ddd transparent;*border-left-color:#ffffff;}
.nav>.disabled>a{color:#dfdfdf;}
.nav>.disabled>a:hover{text-decoration:none;background-color:transparent;cursor:default;}
.navbar{overflow:visible;margin-bottom:20px;*position:relative;*z-index:2;}
.navbar-inner{min-height:50px;padding-left:20px;padding-right:20px;background-color:#080808;background-image:-moz-linear-gradient(top, #080808, #080808);background-image:-webkit-gradient(linear, 0 0, 0 100%, from(#080808), to(#080808));background-image:-webkit-linear-gradient(top, #080808, #080808);background-image:-o-linear-gradient(top, #080808, #080808);background-image:linear-gradient(to bottom, #080808, #080808);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff080808', endColorstr='#ff080808', GradientType=0);border:1px solid transparent;-webkit-border-radius:0px;-moz-border-radius:0px;border-radius:0px;-webkit-box-shadow:0 1px 4px rgba(0, 0, 0, 0.065);-moz-box-shadow:0 1px 4px rgba(0, 0, 0, 0.065);box-shadow:0 1px 4px rgba(0, 0, 0, 0.065);*zoom:1;}.navbar-inner:before,.navbar-inner:after{display:table;content:"";line-height:0;}
.navbar-inner:after{clear:both;}
.navbar .container{width:auto;}
.nav-collapse.collapse{height:auto;overflow:visible;}
.navbar .brand{float:left;display:block;padding:15px 20px 15px;margin-left:-20px;font-size:20px;font-weight:200;color:#ffffff;text-shadow:0 1px 0 #080808;}.navbar .brand:hover{text-decoration:none;}
.navbar-text{margin-bottom:0;line-height:50px;color:#ffffff;}
.navbar-link{color:#ffffff;}.navbar-link:hover{color:#bbbbbb;}
.navbar .divider-vertical{height:50px;margin:0 9px;border-left:1px solid #080808;border-right:1px solid #080808;}
.navbar .btn,.navbar .btn-group{margin-top:10px;}
.navbar .btn-group .btn,.navbar .input-prepend .btn,.navbar .input-append .btn{margin-top:0;}
.navbar-form{margin-bottom:0;*zoom:1;}.navbar-form:before,.navbar-form:after{display:table;content:"";line-height:0;}
.navbar-form:after{clear:both;}
.navbar-form input,.navbar-form select,.navbar-form .radio,.navbar-form .checkbox{margin-top:10px;}
.navbar-form input,.navbar-form select,.navbar-form .btn{display:inline-block;margin-bottom:0;}
.navbar-form input[type="image"],.navbar-form input[type="checkbox"],.navbar-form input[type="radio"]{margin-top:3px;}
.navbar-form .input-append,.navbar-form .input-prepend{margin-top:5px;white-space:nowrap;}.navbar-form .input-append input,.navbar-form .input-prepend input{margin-top:0;}
.navbar-search{position:relative;float:left;margin-top:10px;margin-bottom:0;}.navbar-search .search-query{margin-bottom:0;padding:4px 14px;font-family:"Open Sans",Calibri,Candara,Arial,sans-serif;font-size:13px;font-weight:normal;line-height:1;-webkit-border-radius:15px;-moz-border-radius:15px;border-radius:15px;}
.navbar-static-top{position:static;margin-bottom:0;}.navbar-static-top .navbar-inner{-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;}
.navbar-fixed-top,.navbar-fixed-bottom{position:fixed;right:0;left:0;z-index:1030;margin-bottom:0;}
.navbar-fixed-top .navbar-inner,.navbar-static-top .navbar-inner{border-width:0 0 1px;}
.navbar-fixed-bottom .navbar-inner{border-width:1px 0 0;}
.navbar-fixed-top .navbar-inner,.navbar-fixed-bottom .navbar-inner{padding-left:0;padding-right:0;-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;}
.navbar-static-top .container,.navbar-fixed-top .container,.navbar-fixed-bottom .container{width:940px;}
.navbar-fixed-top{top:0;}
.navbar-fixed-top .navbar-inner,.navbar-static-top .navbar-inner{-webkit-box-shadow:0 1px 10px rgba(0,0,0,.1);-moz-box-shadow:0 1px 10px rgba(0,0,0,.1);box-shadow:0 1px 10px rgba(0,0,0,.1);}
.navbar-fixed-bottom{bottom:0;}.navbar-fixed-bottom .navbar-inner{-webkit-box-shadow:0 -1px 10px rgba(0,0,0,.1);-moz-box-shadow:0 -1px 10px rgba(0,0,0,.1);box-shadow:0 -1px 10px rgba(0,0,0,.1);}
.navbar .nav{position:relative;left:0;display:block;float:left;margin:0 10px 0 0;}
.navbar .nav.pull-right{float:right;margin-right:0;}
.navbar .nav>li{float:left;}
.navbar .nav>li>a{float:none;padding:15px 15px 15px;color:#ffffff;text-decoration:none;text-shadow:0 1px 0 #080808;}
.navbar .nav .dropdown-toggle .caret{margin-top:8px;}
.navbar .nav>li>a:focus,.navbar .nav>li>a:hover{background-color:rgba(0, 0, 0, 0.05);color:#bbbbbb;text-decoration:none;}
.navbar .nav>.active>a,.navbar .nav>.active>a:hover,.navbar .nav>.active>a:focus{color:#ffffff;text-decoration:none;background-color:transparent;-webkit-box-shadow:inset 0 3px 8px rgba(0, 0, 0, 0.125);-moz-box-shadow:inset 0 3px 8px rgba(0, 0, 0, 0.125);box-shadow:inset 0 3px 8px rgba(0, 0, 0, 0.125);}
.navbar .btn-navbar{display:none;float:right;padding:7px 10px;margin-left:5px;margin-right:5px;color:#ffffff;text-shadow:0 -1px 0 rgba(0, 0, 0, 0.25);background-color:#000000;background-image:-moz-linear-gradient(top, #000000, #000000);background-image:-webkit-gradient(linear, 0 0, 0 100%, from(#000000), to(#000000));background-image:-webkit-linear-gradient(top, #000000, #000000);background-image:-o-linear-gradient(top, #000000, #000000);background-image:linear-gradient(to bottom, #000000, #000000);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff000000', endColorstr='#ff000000', GradientType=0);border-color:#000000 #000000 #000000;border-color:rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);*background-color:#000000;filter:progid:DXImageTransform.Microsoft.gradient(enabled = false);-webkit-box-shadow:inset 0 1px 0 rgba(255,255,255,.1), 0 1px 0 rgba(255,255,255,.075);-moz-box-shadow:inset 0 1px 0 rgba(255,255,255,.1), 0 1px 0 rgba(255,255,255,.075);box-shadow:inset 0 1px 0 rgba(255,255,255,.1), 0 1px 0 rgba(255,255,255,.075);}.navbar .btn-navbar:hover,.navbar .btn-navbar:active,.navbar .btn-navbar.active,.navbar .btn-navbar.disabled,.navbar .btn-navbar[disabled]{color:#ffffff;background-color:#000000;*background-color:#000000;}
.navbar .btn-navbar:active,.navbar .btn-navbar.active{background-color:#000000 \9;}
.navbar .btn-navbar .icon-bar{display:block;width:18px;height:2px;background-color:#f5f5f5;-webkit-border-radius:1px;-moz-border-radius:1px;border-radius:1px;-webkit-box-shadow:0 1px 0 rgba(0, 0, 0, 0.25);-moz-box-shadow:0 1px 0 rgba(0, 0, 0, 0.25);box-shadow:0 1px 0 rgba(0, 0, 0, 0.25);}
.btn-navbar .icon-bar+.icon-bar{margin-top:3px;}
.navbar .nav>li>.dropdown-menu:before{content:'';display:inline-block;border-left:7px solid transparent;border-right:7px solid transparent;border-bottom:7px solid #ccc;border-bottom-color:rgba(0, 0, 0, 0.2);position:absolute;top:-7px;left:9px;}
.navbar .nav>li>.dropdown-menu:after{content:'';display:inline-block;border-left:6px solid transparent;border-right:6px solid transparent;border-bottom:6px solid #ffffff;position:absolute;top:-6px;left:10px;}
.navbar-fixed-bottom .nav>li>.dropdown-menu:before{border-top:7px solid #ccc;border-top-color:rgba(0, 0, 0, 0.2);border-bottom:0;bottom:-7px;top:auto;}
.navbar-fixed-bottom .nav>li>.dropdown-menu:after{border-top:6px solid #ffffff;border-bottom:0;bottom:-6px;top:auto;}
.navbar .nav li.dropdown>a:hover .caret{border-top-color:#ffffff;border-bottom-color:#ffffff;}
.navbar .nav li.dropdown.open>.dropdown-toggle,.navbar .nav li.dropdown.active>.dropdown-toggle,.navbar .nav li.dropdown.open.active>.dropdown-toggle{background-color:transparent;color:#ffffff;}
.navbar .nav li.dropdown>.dropdown-toggle .caret{border-top-color:#ffffff;border-bottom-color:#ffffff;}
.navbar .nav li.dropdown.open>.dropdown-toggle .caret,.navbar .nav li.dropdown.active>.dropdown-toggle .caret,.navbar .nav li.dropdown.open.active>.dropdown-toggle .caret{border-top-color:#ffffff;border-bottom-color:#ffffff;}
.navbar .pull-right>li>.dropdown-menu,.navbar .nav>li>.dropdown-menu.pull-right{left:auto;right:0;}.navbar .pull-right>li>.dropdown-menu:before,.navbar .nav>li>.dropdown-menu.pull-right:before{left:auto;right:12px;}
.navbar .pull-right>li>.dropdown-menu:after,.navbar .nav>li>.dropdown-menu.pull-right:after{left:auto;right:13px;}
.navbar .pull-right>li>.dropdown-menu .dropdown-menu,.navbar .nav>li>.dropdown-menu.pull-right .dropdown-menu{left:auto;right:100%;margin-left:0;margin-right:-1px;-webkit-border-radius:6px 0 6px 6px;-moz-border-radius:6px 0 6px 6px;border-radius:6px 0 6px 6px;}
.navbar-inverse .navbar-inner{background-color:#007fff;background-image:-moz-linear-gradient(top, #007fff, #007fff);background-image:-webkit-gradient(linear, 0 0, 0 100%, from(#007fff), to(#007fff));background-image:-webkit-linear-gradient(top, #007fff, #007fff);background-image:-o-linear-gradient(top, #007fff, #007fff);background-image:linear-gradient(to bottom, #007fff, #007fff);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff007fff', endColorstr='#ff007fff', GradientType=0);border-color:transparent;}
.navbar-inverse .brand,.navbar-inverse .nav>li>a{color:#ffffff;text-shadow:0 -1px 0 rgba(0, 0, 0, 0.25);}.navbar-inverse .brand:hover,.navbar-inverse .nav>li>a:hover{color:#ffffff;}
.navbar-inverse .brand{color:#ffffff;}
.navbar-inverse .navbar-text{color:#ffffff;}
.navbar-inverse .nav>li>a:focus,.navbar-inverse .nav>li>a:hover{background-color:rgba(0, 0, 0, 0.05);color:#ffffff;}
.navbar-inverse .nav .active>a,.navbar-inverse .nav .active>a:hover,.navbar-inverse .nav .active>a:focus{color:#ffffff;background-color:#007fff;}
.navbar-inverse .navbar-link{color:#ffffff;}.navbar-inverse .navbar-link:hover{color:#ffffff;}
.navbar-inverse .divider-vertical{border-left-color:#007fff;border-right-color:#007fff;}
.navbar-inverse .nav li.dropdown.open>.dropdown-toggle,.navbar-inverse .nav li.dropdown.active>.dropdown-toggle,.navbar-inverse .nav li.dropdown.open.active>.dropdown-toggle{background-color:#007fff;color:#ffffff;}
.navbar-inverse .nav li.dropdown>a:hover .caret{border-top-color:#ffffff;border-bottom-color:#ffffff;}
.navbar-inverse .nav li.dropdown>.dropdown-toggle .caret{border-top-color:#ffffff;border-bottom-color:#ffffff;}
.navbar-inverse .nav li.dropdown.open>.dropdown-toggle .caret,.navbar-inverse .nav li.dropdown.active>.dropdown-toggle .caret,.navbar-inverse .nav li.dropdown.open.active>.dropdown-toggle .caret{border-top-color:#ffffff;border-bottom-color:#ffffff;}
.navbar-inverse .navbar-search .search-query{color:#ffffff;background-color:#80bfff;border-color:#007fff;-webkit-box-shadow:inset 0 1px 2px rgba(0,0,0,.1), 0 1px 0 rgba(255,255,255,.15);-moz-box-shadow:inset 0 1px 2px rgba(0,0,0,.1), 0 1px 0 rgba(255,255,255,.15);box-shadow:inset 0 1px 2px rgba(0,0,0,.1), 0 1px 0 rgba(255,255,255,.15);-webkit-transition:none;-moz-transition:none;-o-transition:none;transition:none;}.navbar-inverse .navbar-search .search-query:-moz-placeholder{color:#999999;}
.navbar-inverse .navbar-search .search-query:-ms-input-placeholder{color:#999999;}
.navbar-inverse .navbar-search .search-query::-webkit-input-placeholder{color:#999999;}
.navbar-inverse .navbar-search .search-query:focus,.navbar-inverse .navbar-search .search-query.focused{padding:5px 15px;color:#999999;text-shadow:0 1px 0 #ffffff;background-color:#ffffff;border:0;-webkit-box-shadow:0 0 3px rgba(0, 0, 0, 0.15);-moz-box-shadow:0 0 3px rgba(0, 0, 0, 0.15);box-shadow:0 0 3px rgba(0, 0, 0, 0.15);outline:0;}
.navbar-inverse .btn-navbar{color:#ffffff;text-shadow:0 -1px 0 rgba(0, 0, 0, 0.25);background-color:#0072e6;background-image:-moz-linear-gradient(top, #0072e6, #0072e6);background-image:-webkit-gradient(linear, 0 0, 0 100%, from(#0072e6), to(#0072e6));background-image:-webkit-linear-gradient(top, #0072e6, #0072e6);background-image:-o-linear-gradient(top, #0072e6, #0072e6);background-image:linear-gradient(to bottom, #0072e6, #0072e6);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff0072e6', endColorstr='#ff0072e6', GradientType=0);border-color:#0072e6 #0072e6 #004c99;border-color:rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);*background-color:#0072e6;filter:progid:DXImageTransform.Microsoft.gradient(enabled = false);}.navbar-inverse .btn-navbar:hover,.navbar-inverse .btn-navbar:active,.navbar-inverse .btn-navbar.active,.navbar-inverse .btn-navbar.disabled,.navbar-inverse .btn-navbar[disabled]{color:#ffffff;background-color:#0072e6;*background-color:#0066cc;}
.navbar-inverse .btn-navbar:active,.navbar-inverse .btn-navbar.active{background-color:#0059b3 \9;}
.breadcrumb{padding:8px 15px;margin:0 0 20px;list-style:none;background-color:#f5f5f5;-webkit-border-radius:0px;-moz-border-radius:0px;border-radius:0px;}.breadcrumb>li{display:inline-block;*display:inline;*zoom:1;text-shadow:0 1px 0 #ffffff;}.breadcrumb>li>.divider{padding:0 5px;color:#ccc;}
.breadcrumb>.active{color:#dfdfdf;}
.pagination{margin:20px 0;}
.pagination ul{display:inline-block;*display:inline;*zoom:1;margin-left:0;margin-bottom:0;-webkit-border-radius:0px;-moz-border-radius:0px;border-radius:0px;-webkit-box-shadow:0 1px 2px rgba(0, 0, 0, 0.05);-moz-box-shadow:0 1px 2px rgba(0, 0, 0, 0.05);box-shadow:0 1px 2px rgba(0, 0, 0, 0.05);}
.pagination ul>li{display:inline;}
.pagination ul>li>a,.pagination ul>li>span{float:left;padding:4px 12px;line-height:20px;text-decoration:none;background-color:#dfdfdf;border:1px solid transparent;border-left-width:0;}
.pagination ul>li>a:hover,.pagination ul>.active>a,.pagination ul>.active>span{background-color:#007fff;}
.pagination ul>.active>a,.pagination ul>.active>span{color:#dfdfdf;cursor:default;}
.pagination ul>.disabled>span,.pagination ul>.disabled>a,.pagination ul>.disabled>a:hover{color:#dfdfdf;background-color:transparent;cursor:default;}
.pagination ul>li:first-child>a,.pagination ul>li:first-child>span{border-left-width:1px;-webkit-border-top-left-radius:0px;-moz-border-radius-topleft:0px;border-top-left-radius:0px;-webkit-border-bottom-left-radius:0px;-moz-border-radius-bottomleft:0px;border-bottom-left-radius:0px;}
.pagination ul>li:last-child>a,.pagination ul>li:last-child>span{-webkit-border-top-right-radius:0px;-moz-border-radius-topright:0px;border-top-right-radius:0px;-webkit-border-bottom-right-radius:0px;-moz-border-radius-bottomright:0px;border-bottom-right-radius:0px;}
.pagination-centered{text-align:center;}
.pagination-right{text-align:right;}
.pagination-large ul>li>a,.pagination-large ul>li>span{padding:22px 30px;font-size:17.5px;}
.pagination-large ul>li:first-child>a,.pagination-large ul>li:first-child>span{-webkit-border-top-left-radius:0px;-moz-border-radius-topleft:0px;border-top-left-radius:0px;-webkit-border-bottom-left-radius:0px;-moz-border-radius-bottomleft:0px;border-bottom-left-radius:0px;}
.pagination-large ul>li:last-child>a,.pagination-large ul>li:last-child>span{-webkit-border-top-right-radius:0px;-moz-border-radius-topright:0px;border-top-right-radius:0px;-webkit-border-bottom-right-radius:0px;-moz-border-radius-bottomright:0px;border-bottom-right-radius:0px;}
.pagination-mini ul>li:first-child>a,.pagination-small ul>li:first-child>a,.pagination-mini ul>li:first-child>span,.pagination-small ul>li:first-child>span{-webkit-border-top-left-radius:0px;-moz-border-radius-topleft:0px;border-top-left-radius:0px;-webkit-border-bottom-left-radius:0px;-moz-border-radius-bottomleft:0px;border-bottom-left-radius:0px;}
.pagination-mini ul>li:last-child>a,.pagination-small ul>li:last-child>a,.pagination-mini ul>li:last-child>span,.pagination-small ul>li:last-child>span{-webkit-border-top-right-radius:0px;-moz-border-radius-topright:0px;border-top-right-radius:0px;-webkit-border-bottom-right-radius:0px;-moz-border-radius-bottomright:0px;border-bottom-right-radius:0px;}
.pagination-small ul>li>a,.pagination-small ul>li>span{padding:2px 10px;font-size:11.9px;}
.pagination-mini ul>li>a,.pagination-mini ul>li>span{padding:2px 6px;font-size:10.5px;}
.pager{margin:20px 0;list-style:none;text-align:center;*zoom:1;}.pager:before,.pager:after{display:table;content:"";line-height:0;}
.pager:after{clear:both;}
.pager li{display:inline;}
.pager li>a,.pager li>span{display:inline-block;padding:5px 14px;background-color:#fff;border:1px solid #ddd;-webkit-border-radius:15px;-moz-border-radius:15px;border-radius:15px;}
.pager li>a:hover{text-decoration:none;background-color:#f5f5f5;}
.pager .next>a,.pager .next>span{float:right;}
.pager .previous>a,.pager .previous>span{float:left;}
.pager .disabled>a,.pager .disabled>a:hover,.pager .disabled>span{color:#dfdfdf;background-color:#fff;cursor:default;}
.modal-backdrop{position:fixed;top:0;right:0;bottom:0;left:0;z-index:1040;background-color:#000000;}.modal-backdrop.fade{opacity:0;}
.modal-backdrop,.modal-backdrop.fade.in{opacity:0.8;filter:alpha(opacity=80);}
.modal{position:fixed;top:10%;left:50%;z-index:1050;width:560px;margin-left:-280px;background-color:#ffffff;border:1px solid #999;border:1px solid rgba(0, 0, 0, 0.3);*border:1px solid #999;-webkit-border-radius:6px;-moz-border-radius:6px;border-radius:6px;-webkit-box-shadow:0 3px 7px rgba(0, 0, 0, 0.3);-moz-box-shadow:0 3px 7px rgba(0, 0, 0, 0.3);box-shadow:0 3px 7px rgba(0, 0, 0, 0.3);-webkit-background-clip:padding-box;-moz-background-clip:padding-box;background-clip:padding-box;outline:none;}.modal.fade{-webkit-transition:opacity .3s linear, top .3s ease-out;-moz-transition:opacity .3s linear, top .3s ease-out;-o-transition:opacity .3s linear, top .3s ease-out;transition:opacity .3s linear, top .3s ease-out;top:-25%;}
.modal.fade.in{top:10%;}
.modal-header{padding:9px 15px;border-bottom:1px solid #eee;}.modal-header .close{margin-top:2px;}
.modal-header h3{margin:0;line-height:30px;}
.modal-body{position:relative;overflow-y:auto;max-height:400px;padding:15px;}
.modal-form{margin-bottom:0;}
.modal-footer{padding:14px 15px 15px;margin-bottom:0;text-align:right;background-color:#f5f5f5;border-top:1px solid #ddd;-webkit-border-radius:0 0 6px 6px;-moz-border-radius:0 0 6px 6px;border-radius:0 0 6px 6px;-webkit-box-shadow:inset 0 1px 0 #ffffff;-moz-box-shadow:inset 0 1px 0 #ffffff;box-shadow:inset 0 1px 0 #ffffff;*zoom:1;}.modal-footer:before,.modal-footer:after{display:table;content:"";line-height:0;}
.modal-footer:after{clear:both;}
.modal-footer .btn+.btn{margin-left:5px;margin-bottom:0;}
.modal-footer .btn-group .btn+.btn{margin-left:-1px;}
.modal-footer .btn-block+.btn-block{margin-left:0;}
.tooltip{position:absolute;z-index:1030;display:block;visibility:visible;padding:5px;font-size:11px;opacity:0;filter:alpha(opacity=0);}.tooltip.in{opacity:0.8;filter:alpha(opacity=80);}
.tooltip.top{margin-top:-3px;}
.tooltip.right{margin-left:3px;}
.tooltip.bottom{margin-top:3px;}
.tooltip.left{margin-left:-3px;}
.tooltip-inner{max-width:200px;padding:3px 8px;color:#ffffff;text-align:center;text-decoration:none;background-color:#000000;-webkit-border-radius:0px;-moz-border-radius:0px;border-radius:0px;}
.tooltip-arrow{position:absolute;width:0;height:0;border-color:transparent;border-style:solid;}
.tooltip.top .tooltip-arrow{bottom:0;left:50%;margin-left:-5px;border-width:5px 5px 0;border-top-color:#000000;}
.tooltip.right .tooltip-arrow{top:50%;left:0;margin-top:-5px;border-width:5px 5px 5px 0;border-right-color:#000000;}
.tooltip.left .tooltip-arrow{top:50%;right:0;margin-top:-5px;border-width:5px 0 5px 5px;border-left-color:#000000;}
.tooltip.bottom .tooltip-arrow{top:0;left:50%;margin-left:-5px;border-width:0 5px 5px;border-bottom-color:#000000;}
.popover{position:absolute;top:0;left:0;z-index:1010;display:none;width:236px;padding:1px;text-align:left;background-color:#ff7518;-webkit-background-clip:padding-box;-moz-background-clip:padding;background-clip:padding-box;border:1px solid #ccc;border:1px solid rgba(0, 0, 0, 0.2);-webkit-border-radius:6px;-moz-border-radius:6px;border-radius:6px;-webkit-box-shadow:0 5px 10px rgba(0, 0, 0, 0.2);-moz-box-shadow:0 5px 10px rgba(0, 0, 0, 0.2);box-shadow:0 5px 10px rgba(0, 0, 0, 0.2);white-space:normal;}.popover.top{margin-top:-10px;}
.popover.right{margin-left:10px;}
.popover.bottom{margin-top:10px;}
.popover.left{margin-left:-10px;}
.popover-title{margin:0;padding:8px 14px;font-size:14px;font-weight:normal;line-height:18px;background-color:#ff7518;border-bottom:1px solid #fe6600;-webkit-border-radius:5px 5px 0 0;-moz-border-radius:5px 5px 0 0;border-radius:5px 5px 0 0;}
.popover-content{padding:9px 14px;}
.popover .arrow,.popover .arrow:after{position:absolute;display:block;width:0;height:0;border-color:transparent;border-style:solid;}
.popover .arrow{border-width:16px;}
.popover .arrow:after{border-width:15px;content:"";}
.popover.top .arrow{left:50%;margin-left:-16px;border-bottom-width:0;border-top-color:#999;border-top-color:transparent;bottom:-16px;}.popover.top .arrow:after{bottom:1px;margin-left:-15px;border-bottom-width:0;border-top-color:#ff7518;}
.popover.right .arrow{top:50%;left:-16px;margin-top:-16px;border-left-width:0;border-right-color:#999;border-right-color:transparent;}.popover.right .arrow:after{left:1px;bottom:-15px;border-left-width:0;border-right-color:#ff7518;}
.popover.bottom .arrow{left:50%;margin-left:-16px;border-top-width:0;border-bottom-color:#999;border-bottom-color:transparent;top:-16px;}.popover.bottom .arrow:after{top:1px;margin-left:-15px;border-top-width:0;border-bottom-color:#ff7518;}
.popover.left .arrow{top:50%;right:-16px;margin-top:-16px;border-right-width:0;border-left-color:#999;border-left-color:transparent;}.popover.left .arrow:after{right:1px;border-right-width:0;border-left-color:#ff7518;bottom:-15px;}
.thumbnails{margin-left:-20px;list-style:none;*zoom:1;}.thumbnails:before,.thumbnails:after{display:table;content:"";line-height:0;}
.thumbnails:after{clear:both;}
.row-fluid .thumbnails{margin-left:0;}
.thumbnails>li{float:left;margin-bottom:20px;margin-left:20px;}
.thumbnail{display:block;padding:4px;line-height:20px;border:1px solid #ddd;-webkit-border-radius:0px;-moz-border-radius:0px;border-radius:0px;-webkit-box-shadow:0 1px 3px rgba(0, 0, 0, 0.055);-moz-box-shadow:0 1px 3px rgba(0, 0, 0, 0.055);box-shadow:0 1px 3px rgba(0, 0, 0, 0.055);-webkit-transition:all 0.2s ease-in-out;-moz-transition:all 0.2s ease-in-out;-o-transition:all 0.2s ease-in-out;transition:all 0.2s ease-in-out;}
a.thumbnail:hover{border-color:#007fff;-webkit-box-shadow:0 1px 4px rgba(0, 105, 214, 0.25);-moz-box-shadow:0 1px 4px rgba(0, 105, 214, 0.25);box-shadow:0 1px 4px rgba(0, 105, 214, 0.25);}
.thumbnail>img{display:block;max-width:100%;margin-left:auto;margin-right:auto;}
.thumbnail .caption{padding:9px;color:#bbbbbb;}
.media,.media-body{overflow:hidden;*overflow:visible;zoom:1;}
.media,.media .media{margin-top:15px;}
.media:first-child{margin-top:0;}
.media-object{display:block;}
.media-heading{margin:0 0 5px;}
.media .pull-left{margin-right:10px;}
.media .pull-right{margin-left:10px;}
.media-list{margin-left:0;list-style:none;}
.label,.badge{display:inline-block;padding:2px 4px;font-size:11.844px;font-weight:bold;line-height:14px;color:#ffffff;vertical-align:baseline;white-space:nowrap;text-shadow:0 -1px 0 rgba(0, 0, 0, 0.25);background-color:#dfdfdf;}
.label{-webkit-border-radius:3px;-moz-border-radius:3px;border-radius:3px;}
.badge{padding-left:9px;padding-right:9px;-webkit-border-radius:9px;-moz-border-radius:9px;border-radius:9px;}
.label:empty,.badge:empty{display:none;}
a.label:hover,a.badge:hover{color:#ffffff;text-decoration:none;cursor:pointer;}
.label-important,.badge-important{background-color:#ffffff;}
.label-important[href],.badge-important[href]{background-color:#e6e6e6;}
.label-warning,.badge-warning{background-color:#ff7518;}
.label-warning[href],.badge-warning[href]{background-color:#e45c00;}
.label-success,.badge-success{background-color:#ffffff;}
.label-success[href],.badge-success[href]{background-color:#e6e6e6;}
.label-info,.badge-info{background-color:#ffffff;}
.label-info[href],.badge-info[href]{background-color:#e6e6e6;}
.label-inverse,.badge-inverse{background-color:#999999;}
.label-inverse[href],.badge-inverse[href]{background-color:#808080;}
.btn .label,.btn .badge{position:relative;top:-1px;}
.btn-mini .label,.btn-mini .badge{top:0;}
@-webkit-keyframes progress-bar-stripes{from{background-position:40px 0;} to{background-position:0 0;}}@-moz-keyframes progress-bar-stripes{from{background-position:40px 0;} to{background-position:0 0;}}@-ms-keyframes progress-bar-stripes{from{background-position:40px 0;} to{background-position:0 0;}}@-o-keyframes progress-bar-stripes{from{background-position:0 0;} to{background-position:40px 0;}}@keyframes progress-bar-stripes{from{background-position:40px 0;} to{background-position:0 0;}}.progress{overflow:hidden;height:20px;margin-bottom:20px;background-color:#f7f7f7;background-image:-moz-linear-gradient(top, #f5f5f5, #f9f9f9);background-image:-webkit-gradient(linear, 0 0, 0 100%, from(#f5f5f5), to(#f9f9f9));background-image:-webkit-linear-gradient(top, #f5f5f5, #f9f9f9);background-image:-o-linear-gradient(top, #f5f5f5, #f9f9f9);background-image:linear-gradient(to bottom, #f5f5f5, #f9f9f9);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#fff5f5f5', endColorstr='#fff9f9f9', GradientType=0);-webkit-box-shadow:inset 0 1px 2px rgba(0, 0, 0, 0.1);-moz-box-shadow:inset 0 1px 2px rgba(0, 0, 0, 0.1);box-shadow:inset 0 1px 2px rgba(0, 0, 0, 0.1);-webkit-border-radius:0px;-moz-border-radius:0px;border-radius:0px;}
.progress .bar{width:0%;height:100%;color:#ffffff;float:left;font-size:12px;text-align:center;text-shadow:0 -1px 0 rgba(0, 0, 0, 0.25);background-color:#0e90d2;background-image:-moz-linear-gradient(top, #149bdf, #0480be);background-image:-webkit-gradient(linear, 0 0, 0 100%, from(#149bdf), to(#0480be));background-image:-webkit-linear-gradient(top, #149bdf, #0480be);background-image:-o-linear-gradient(top, #149bdf, #0480be);background-image:linear-gradient(to bottom, #149bdf, #0480be);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff149bdf', endColorstr='#ff0480be', GradientType=0);-webkit-box-shadow:inset 0 -1px 0 rgba(0, 0, 0, 0.15);-moz-box-shadow:inset 0 -1px 0 rgba(0, 0, 0, 0.15);box-shadow:inset 0 -1px 0 rgba(0, 0, 0, 0.15);-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box;-webkit-transition:width 0.6s ease;-moz-transition:width 0.6s ease;-o-transition:width 0.6s ease;transition:width 0.6s ease;}
.progress .bar+.bar{-webkit-box-shadow:inset 1px 0 0 rgba(0,0,0,.15), inset 0 -1px 0 rgba(0,0,0,.15);-moz-box-shadow:inset 1px 0 0 rgba(0,0,0,.15), inset 0 -1px 0 rgba(0,0,0,.15);box-shadow:inset 1px 0 0 rgba(0,0,0,.15), inset 0 -1px 0 rgba(0,0,0,.15);}
.progress-striped .bar{background-color:#149bdf;background-image:-webkit-gradient(linear, 0 100%, 100% 0, color-stop(0.25, rgba(255, 255, 255, 0.15)), color-stop(0.25, transparent), color-stop(0.5, transparent), color-stop(0.5, rgba(255, 255, 255, 0.15)), color-stop(0.75, rgba(255, 255, 255, 0.15)), color-stop(0.75, transparent), to(transparent));background-image:-webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);background-image:-moz-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);background-image:-o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);background-image:linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);-webkit-background-size:40px 40px;-moz-background-size:40px 40px;-o-background-size:40px 40px;background-size:40px 40px;}
.progress.active .bar{-webkit-animation:progress-bar-stripes 2s linear infinite;-moz-animation:progress-bar-stripes 2s linear infinite;-ms-animation:progress-bar-stripes 2s linear infinite;-o-animation:progress-bar-stripes 2s linear infinite;animation:progress-bar-stripes 2s linear infinite;}
.progress-danger .bar,.progress .bar-danger{background-color:#dd514c;background-image:-moz-linear-gradient(top, #ee5f5b, #c43c35);background-image:-webkit-gradient(linear, 0 0, 0 100%, from(#ee5f5b), to(#c43c35));background-image:-webkit-linear-gradient(top, #ee5f5b, #c43c35);background-image:-o-linear-gradient(top, #ee5f5b, #c43c35);background-image:linear-gradient(to bottom, #ee5f5b, #c43c35);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffee5f5b', endColorstr='#ffc43c35', GradientType=0);}
.progress-danger.progress-striped .bar,.progress-striped .bar-danger{background-color:#ee5f5b;background-image:-webkit-gradient(linear, 0 100%, 100% 0, color-stop(0.25, rgba(255, 255, 255, 0.15)), color-stop(0.25, transparent), color-stop(0.5, transparent), color-stop(0.5, rgba(255, 255, 255, 0.15)), color-stop(0.75, rgba(255, 255, 255, 0.15)), color-stop(0.75, transparent), to(transparent));background-image:-webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);background-image:-moz-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);background-image:-o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);background-image:linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);}
.progress-success .bar,.progress .bar-success{background-color:#5eb95e;background-image:-moz-linear-gradient(top, #62c462, #57a957);background-image:-webkit-gradient(linear, 0 0, 0 100%, from(#62c462), to(#57a957));background-image:-webkit-linear-gradient(top, #62c462, #57a957);background-image:-o-linear-gradient(top, #62c462, #57a957);background-image:linear-gradient(to bottom, #62c462, #57a957);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff62c462', endColorstr='#ff57a957', GradientType=0);}
.progress-success.progress-striped .bar,.progress-striped .bar-success{background-color:#62c462;background-image:-webkit-gradient(linear, 0 100%, 100% 0, color-stop(0.25, rgba(255, 255, 255, 0.15)), color-stop(0.25, transparent), color-stop(0.5, transparent), color-stop(0.5, rgba(255, 255, 255, 0.15)), color-stop(0.75, rgba(255, 255, 255, 0.15)), color-stop(0.75, transparent), to(transparent));background-image:-webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);background-image:-moz-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);background-image:-o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);background-image:linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);}
.progress-info .bar,.progress .bar-info{background-color:#4bb1cf;background-image:-moz-linear-gradient(top, #5bc0de, #339bb9);background-image:-webkit-gradient(linear, 0 0, 0 100%, from(#5bc0de), to(#339bb9));background-image:-webkit-linear-gradient(top, #5bc0de, #339bb9);background-image:-o-linear-gradient(top, #5bc0de, #339bb9);background-image:linear-gradient(to bottom, #5bc0de, #339bb9);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff5bc0de', endColorstr='#ff339bb9', GradientType=0);}
.progress-info.progress-striped .bar,.progress-striped .bar-info{background-color:#5bc0de;background-image:-webkit-gradient(linear, 0 100%, 100% 0, color-stop(0.25, rgba(255, 255, 255, 0.15)), color-stop(0.25, transparent), color-stop(0.5, transparent), color-stop(0.5, rgba(255, 255, 255, 0.15)), color-stop(0.75, rgba(255, 255, 255, 0.15)), color-stop(0.75, transparent), to(transparent));background-image:-webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);background-image:-moz-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);background-image:-o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);background-image:linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);}
.progress-warning .bar,.progress .bar-warning{background-color:#ff9046;background-image:-moz-linear-gradient(top, #ffa365, #ff7518);background-image:-webkit-gradient(linear, 0 0, 0 100%, from(#ffa365), to(#ff7518));background-image:-webkit-linear-gradient(top, #ffa365, #ff7518);background-image:-o-linear-gradient(top, #ffa365, #ff7518);background-image:linear-gradient(to bottom, #ffa365, #ff7518);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffffa365', endColorstr='#ffff7518', GradientType=0);}
.progress-warning.progress-striped .bar,.progress-striped .bar-warning{background-color:#ffa365;background-image:-webkit-gradient(linear, 0 100%, 100% 0, color-stop(0.25, rgba(255, 255, 255, 0.15)), color-stop(0.25, transparent), color-stop(0.5, transparent), color-stop(0.5, rgba(255, 255, 255, 0.15)), color-stop(0.75, rgba(255, 255, 255, 0.15)), color-stop(0.75, transparent), to(transparent));background-image:-webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);background-image:-moz-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);background-image:-o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);background-image:linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);}
.accordion{margin-bottom:20px;}
.accordion-group{margin-bottom:2px;border:1px solid #e5e5e5;-webkit-border-radius:0px;-moz-border-radius:0px;border-radius:0px;}
.accordion-heading{border-bottom:0;}
.accordion-heading .accordion-toggle{display:block;padding:8px 15px;}
.accordion-toggle{cursor:pointer;}
.accordion-inner{padding:9px 15px;border-top:1px solid #e5e5e5;}
.carousel{position:relative;margin-bottom:20px;line-height:1;}
.carousel-inner{overflow:hidden;width:100%;position:relative;}
.carousel-inner>.item{display:none;position:relative;-webkit-transition:0.6s ease-in-out left;-moz-transition:0.6s ease-in-out left;-o-transition:0.6s ease-in-out left;transition:0.6s ease-in-out left;}
.carousel-inner>.item>img{display:block;line-height:1;}
.carousel-inner>.active,.carousel-inner>.next,.carousel-inner>.prev{display:block;}
.carousel-inner>.active{left:0;}
.carousel-inner>.next,.carousel-inner>.prev{position:absolute;top:0;width:100%;}
.carousel-inner>.next{left:100%;}
.carousel-inner>.prev{left:-100%;}
.carousel-inner>.next.left,.carousel-inner>.prev.right{left:0;}
.carousel-inner>.active.left{left:-100%;}
.carousel-inner>.active.right{left:100%;}
.carousel-control{position:absolute;top:40%;left:15px;width:40px;height:40px;margin-top:-20px;font-size:60px;font-weight:100;line-height:30px;color:#ffffff;text-align:center;background:#080808;border:3px solid #ffffff;-webkit-border-radius:23px;-moz-border-radius:23px;border-radius:23px;opacity:0.5;filter:alpha(opacity=50);}.carousel-control.right{left:auto;right:15px;}
.carousel-control:hover{color:#ffffff;text-decoration:none;opacity:0.9;filter:alpha(opacity=90);}
.carousel-caption{position:absolute;left:0;right:0;bottom:0;padding:15px;background:#999999;background:rgba(0, 0, 0, 0.75);}
.carousel-caption h4,.carousel-caption p{color:#ffffff;line-height:20px;}
.carousel-caption h4{margin:0 0 5px;}
.carousel-caption p{margin-bottom:0;}
.hero-unit{padding:60px;margin-bottom:30px;font-size:18px;font-weight:200;line-height:30px;color:inherit;background-color:#eeeeee;-webkit-border-radius:6px;-moz-border-radius:6px;border-radius:6px;}.hero-unit h1{margin-bottom:0;font-size:60px;line-height:1;color:inherit;letter-spacing:-1px;}
.hero-unit li{line-height:30px;}
.pull-right{float:right;}
.pull-left{float:left;}
.hide{display:none;}
.show{display:block;}
.invisible{visibility:hidden;}
.affix{position:fixed;}
body{font-weight:300;}
h1{font-size:50px;}
h2,h3{font-size:26px;}
h4{font-size:14px;}
h5,h6{font-size:11px;}
blockquote{padding:10px 15px;background-color:#eeeeee;border-left-color:#bbbbbb;}blockquote.pull-right{padding:10px 15px;border-right-color:#bbbbbb;}
blockquote small{color:#bbbbbb;}
.muted{color:#bbbbbb;}
.navbar .navbar-inner{background-image:none;-webkit-box-shadow:none;-moz-box-shadow:none;box-shadow:none;-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;}
.navbar .brand:hover{color:#bbbbbb;}
.navbar .nav>.active>a,.navbar .nav>.active>a:hover,.navbar .nav>.active>a:focus{-webkit-box-shadow:none;-moz-box-shadow:none;box-shadow:none;background-color:rgba(0, 0, 0, 0.05);}
.navbar .nav li.dropdown.open>.dropdown-toggle,.navbar .nav li.dropdown.active>.dropdown-toggle,.navbar .nav li.dropdown.open.active>.dropdown-toggle{color:#ffffff;}.navbar .nav li.dropdown.open>.dropdown-toggle:hover,.navbar .nav li.dropdown.active>.dropdown-toggle:hover,.navbar .nav li.dropdown.open.active>.dropdown-toggle:hover{color:#eeeeee;}
.navbar .navbar-search .search-query{line-height:normal;}
.navbar-inverse .brand,.navbar-inverse .nav>li>a{text-shadow:none;}
.navbar-inverse .brand:hover,.navbar-inverse .nav>.active>a,.navbar-inverse .nav>.active>a:hover,.navbar-inverse .nav>.active>a:focus{background-color:rgba(0, 0, 0, 0.05);-webkit-box-shadow:none;-moz-box-shadow:none;box-shadow:none;color:#ffffff;}
.navbar-inverse .navbar-search .search-query{color:#080808;}
div.subnav{background-color:#dfdfdf;background-image:none;-webkit-box-shadow:none;-moz-box-shadow:none;box-shadow:none;border:none;-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;}div.subnav .nav{background-color:transparent;}
div.subnav .nav>li>a{border-color:transparent;}
div.subnav .nav>.active>a,div.subnav .nav>.active>a:hover{border-color:transparent;background-color:#000000;color:#ffffff;-webkit-box-shadow:none;-moz-box-shadow:none;box-shadow:none;}
div.subnav-fixed{top:50px;}
.nav .open .dropdown-toggle,.nav >li.dropdown.open.active>a:hover{color:#007fff;}
.nav-tabs >li>a{-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;}
.nav-tabs.nav-stacked >li>a:hover{background-color:#007fff;color:#ffffff;}
.nav-tabs.nav-stacked >.active>a,.nav-tabs.nav-stacked >.active>a:hover{background-color:#ffffff;color:#bbbbbb;}
.nav-tabs.nav-stacked >li:first-child>a,.nav-tabs.nav-stacked >li:last-child>a{-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;}
.nav-pills >li>a{background-color:#dfdfdf;-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;color:#000000;}.nav-pills >li>a:hover{background-color:#000000;color:#ffffff;}
.nav-pills >.disabled>a,.nav-pills >.disabled>a:hover{background-color:#eeeeee;color:#999999;}
.nav-list >li>a{color:#080808;}.nav-list >li>a:hover{background-color:#007fff;color:#ffffff;text-shadow:none;}
.nav-list .nav-header{color:#080808;}
.nav-list .divider{background-color:#bbbbbb;border-bottom:none;}
.pagination ul{-webkit-box-shadow:none;-moz-box-shadow:none;box-shadow:none;}.pagination ul >li>a,.pagination ul >li>span{margin-right:6px;color:#080808;}.pagination ul >li>a:hover,.pagination ul >li>span:hover{background-color:#080808;color:#ffffff;}
.pagination ul >li:last-child>a,.pagination ul >li:last-child>span{margin-right:0;}
.pagination ul >.active>a,.pagination ul >.active>span{color:#ffffff;}
.pagination ul >.disabled>span,.pagination ul >.disabled>a,.pagination ul >.disabled>a:hover{background-color:#eeeeee;color:#999999;}
.pager li>a,.pager li>span{background-color:#dfdfdf;border:none;-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;color:#080808;}.pager li>a:hover,.pager li>span:hover{background-color:#080808;color:#ffffff;}
.pager .disabled>a,.pager .disabled>a:hover,.pager .disabled>span{background-color:#eeeeee;color:#999999;}
.breadcrumb{background-color:#dfdfdf;}.breadcrumb li{text-shadow:none;}
.breadcrumb .divider,.breadcrumb .active{color:#080808;text-shadow:none;}
.btn{padding:5px 12px;background-image:none;-webkit-box-shadow:none;-moz-box-shadow:none;box-shadow:none;border:none;-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;text-shadow:none;}.btn.disabled{box-shadow:inset 0 2px 4px rgba(0, 0, 0, 0.15), 0 1px 2px rgba(0, 0, 0, 0.05);}
.btn-large{padding:22px 30px;}
.btn-small{padding:2px 10px;}
.btn-mini{padding:2px 6px;}
.btn-group >.btn:first-child,.btn-group >.btn:last-child,.btn-group >.dropdown-toggle{-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;}
.btn-group >.btn+.dropdown-toggle{-webkit-box-shadow:none;-moz-box-shadow:none;box-shadow:none;}
.table tbody tr.success td{color:#ffffff;}
.table tbody tr.error td{color:#ffffff;}
.table tbody tr.info td{color:#ffffff;}
.table-bordered{-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;}.table-bordered thead:first-child tr:first-child th:first-child,.table-bordered tbody:first-child tr:first-child td:first-child{-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;}
.table-bordered thead:last-child tr:last-child th:first-child,.table-bordered tbody:last-child tr:last-child td:first-child,.table-bordered tfoot:last-child tr:last-child td:first-child{-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;}
select,textarea,input[type="text"],input[type="password"],input[type="datetime"],input[type="datetime-local"],input[type="date"],input[type="month"],input[type="time"],input[type="week"],input[type="number"],input[type="email"],input[type="url"],input[type="search"],input[type="tel"],input[type="color"]{color:#080808;}
.control-group.warning .control-label,.control-group.warning .help-block,.control-group.warning .help-inline{color:#ff7518;}
.control-group.warning input,.control-group.warning select,.control-group.warning textarea{border-color:#ff7518;color:#080808;}
.control-group.error .control-label,.control-group.error .help-block,.control-group.error .help-inline{color:#ff0039;}
.control-group.error input,.control-group.error select,.control-group.error textarea{border-color:#ff0039;color:#080808;}
.control-group.success .control-label,.control-group.success .help-block,.control-group.success .help-inline{color:#3fb618;}
.control-group.success input,.control-group.success select,.control-group.success textarea{border-color:#3fb618;color:#080808;}
legend{border-bottom:none;color:#080808;}
.form-actions{border-top:none;background-color:#eeeeee;}
.dropdown-menu{-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;}
.alert{-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;text-shadow:none;}.alert-heading,.alert h1,.alert h2,.alert h3,.alert h4,.alert h5,.alert h6{color:#ffffff;}
.label{min-width:80px;min-height:80px;-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;font-weight:300;text-shadow:none;}.label-success{background-color:#3fb618;}
.label-important{background-color:#ff0039;}
.label-info{background-color:#9954bb;}
.label-inverse{background-color:#000000;}
.badge{-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;font-weight:300;text-shadow:none;}.badge-success{background-color:#3fb618;}
.badge-important{background-color:#ff0039;}
.badge-info{background-color:#9954bb;}
.badge-inverse{background-color:#000000;}
.hero-unit{border:none;-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;-webkit-box-shadow:none;-moz-box-shadow:none;box-shadow:none;}
.well{border:none;-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;-webkit-box-shadow:none;-moz-box-shadow:none;box-shadow:none;}
[class^="icon-"],[class*=" icon-"]{margin:0 2px;vertical-align:-2px;}
a.thumbnail{background-color:#dfdfdf;}a.thumbnail:hover{background-color:#bbbbbb;border-color:transparent;}
.progress{height:6px;-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;-webkit-box-shadow:none;-moz-box-shadow:none;box-shadow:none;background-color:#eeeeee;background-image:none;}.progress .bar{background-color:#007fff;background-image:none;}
.progress-info{background-color:#9954bb;}
.progress-success{background-color:#3fb618;}
.progress-warning{background-color:#ff7518;}
.progress-danger{background-color:#ff0039;}
.modal{-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;}.modal-header{border-bottom:none;}
.modal-footer{border-top:none;background-color:transparent;}
.popover{-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;color:#ffffff;}.popover-title{border-bottom:none;color:#ffffff;}
.pull-right{float:right;}
.pull-left{float:left;}
.hide{display:none;}
.show{display:block;}
.invisible{visibility:hidden;}
.affix{position:fixed;}

File diff suppressed because one or more lines are too long

View File

@ -1,137 +1,16 @@
a {
color: #3F8ED8;
text-decoration: none;
}
#hd.doc {
-x-system-font:none;
font-family: Helvetica,Arial,Tahoma,Verdana,Sans-Serif;
color: #444444;
margin: 0;
margin-bottom: 1em;
}
#hd.doc h1 {
letter-spacing: 3px;
font-size: 2.5em;
margin: 0.3em 0;
font-weight: normal;
}
#nav {
float: right;
}
#bd {
font: 16px/21px "HelveticaNeue","Helvetica Neue",Helvetica,Arial,sans-serif;
line-height: 1.5;
color: #444444;
}
#bd h1, #bd h2, #bd h3 {
font-family: "Georgia","Times New Roman",Helvetica,Arial,sans-serif;
font-weight: normal;
color: #181818;
}
#bd h1 {
font-size: 1.9em;
border-bottom: 2px solid #ff7033;
margin-top: 5px;
margin-bottom: 5px;
}
#bd h2 {
font-size: 1.4em;
border-bottom: 1px solid #cccccc;
margin-top: 5px;
margin-bottom: 5px;
}
#bd h3 {
margin-bottom: 0px;
}
#bd p {
margin: 1em 0;
margin-top: 0.5em;
}
/* Keyboard shortcuts */
#bd em {
font-weight: bold;
color: #00A700;
font-style: normal;
}
#ft.doc {
color: #aaa;
border-top: 1px solid #aaa;
clear: both;
margin-top: 2em;
font-size: 0.8em;
letter-spacing: 0.5px;
}
.faq .question {
font-size: 1.1em;
font-weight: bold;
}
pre {
font-size: 0.9em;
line-height: 1.4;
padding: 10px;
background-color: #dddddd;
margin: 1em 0;
}
.terminal {
color: #c0c0c0;
font-size: 1em;
background: #000000;
}
.docindex {
font-size: 1.3em;
line-height: 1.3;
margin-top: 0.1em;
margin-bottom: 0;
margin-left: 0px;
pre {
margin-top: 10px;
color: #333;
}
.docindex li {
list-style-position: inside;
margin-left: 0;
}
.docindex ul {
margin-left: 2em;
margin-top: 0.1em;
margin-bottom: 0.1em;
.tablenum {
font-weight: bold;
}
li a {
text-decoration: none;
}
.highlight {
font-size: 14px;
}
.example_legend{
line-height: 1;
font-size: 12px;
}
.example pre {
margin: 0;
}
.kvtable th {
text-align: left;
white-space: nowrap;
}

View File

@ -0,0 +1,572 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>ActiveLayerIndex</key>
<integer>0</integer>
<key>ApplicationVersion</key>
<array>
<string>com.omnigroup.OmniGraffle.MacAppStore</string>
<string>139.16</string>
</array>
<key>AutoAdjust</key>
<true/>
<key>BackgroundGraphic</key>
<dict>
<key>Bounds</key>
<string>{{0, 0}, {559.19998741149902, 782.79998779296875}}</string>
<key>Class</key>
<string>SolidGraphic</string>
<key>ID</key>
<integer>2</integer>
<key>Style</key>
<dict>
<key>shadow</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>stroke</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
</dict>
</dict>
<key>BaseZoom</key>
<integer>0</integer>
<key>CanvasOrigin</key>
<string>{0, 0}</string>
<key>ColumnAlign</key>
<integer>1</integer>
<key>ColumnSpacing</key>
<real>36</real>
<key>CreationDate</key>
<string>2013-01-02 19:31:53 +0000</string>
<key>Creator</key>
<string>Aldo Cortesi</string>
<key>DisplayScale</key>
<string>1.000 cm = 1.000 cm</string>
<key>GraphDocumentVersion</key>
<integer>8</integer>
<key>GraphicsList</key>
<array>
<dict>
<key>Class</key>
<string>LineGraphic</string>
<key>ID</key>
<integer>4074</integer>
<key>Points</key>
<array>
<string>{300.4483540852865, 420.70833897590637}</string>
<string>{344.88497416178387, 420.70833897590654}</string>
<string>{362.21830749511713, 420.04167230923986}</string>
<string>{413.55166625976557, 419.70833905537921}</string>
</array>
<key>Style</key>
<dict>
<key>stroke</key>
<dict>
<key>HeadArrow</key>
<string>FilledArrow</string>
<key>Legacy</key>
<true/>
<key>TailArrow</key>
<string>0</string>
</dict>
</dict>
</dict>
<dict>
<key>Class</key>
<string>LineGraphic</string>
<key>ID</key>
<integer>4070</integer>
<key>Points</key>
<array>
<string>{84.896692911783873, 420.66667453447985}</string>
<string>{129.33331298828122, 420.66667453448002}</string>
<string>{146.66664632161454, 420.00000786781334}</string>
<string>{198.00000508626297, 419.66667461395269}</string>
</array>
<key>Style</key>
<dict>
<key>stroke</key>
<dict>
<key>HeadArrow</key>
<string>FilledArrow</string>
<key>Legacy</key>
<true/>
<key>TailArrow</key>
<string>0</string>
</dict>
</dict>
</dict>
<dict>
<key>Bounds</key>
<string>{{326.00000000000023, 391.39999198913591}, {62, 24}}</string>
<key>Class</key>
<string>ShapedGraphic</string>
<key>FitText</key>
<string>YES</string>
<key>Flow</key>
<string>Resize</string>
<key>FontInfo</key>
<dict>
<key>Font</key>
<string>Helvetica</string>
<key>Size</key>
<real>12</real>
</dict>
<key>ID</key>
<integer>4063</integer>
<key>Shape</key>
<string>Rectangle</string>
<key>Style</key>
<dict>
<key>fill</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>shadow</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>stroke</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
</dict>
<key>Text</key>
<dict>
<key>Pad</key>
<integer>0</integer>
<key>Text</key>
<string>{\rtf1\ansi\ansicpg1252\cocoartf1187\cocoasubrtf340
\cocoascreenfonts1{\fonttbl\f0\fswiss\fcharset0 Helvetica;}
{\colortbl;\red255\green255\blue255;}
\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc
\f0\fs20 \cf0 2: Forwarded \
Request}</string>
<key>VerticalPad</key>
<integer>0</integer>
</dict>
<key>Wrap</key>
<string>NO</string>
</dict>
<dict>
<key>Bounds</key>
<string>{{110, 403.39997863769622}, {49, 12}}</string>
<key>Class</key>
<string>ShapedGraphic</string>
<key>FitText</key>
<string>YES</string>
<key>Flow</key>
<string>Resize</string>
<key>FontInfo</key>
<dict>
<key>Font</key>
<string>Helvetica</string>
<key>Size</key>
<real>12</real>
</dict>
<key>ID</key>
<integer>4061</integer>
<key>Shape</key>
<string>Rectangle</string>
<key>Style</key>
<dict>
<key>fill</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>shadow</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>stroke</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
</dict>
<key>Text</key>
<dict>
<key>Pad</key>
<integer>0</integer>
<key>Text</key>
<string>{\rtf1\ansi\ansicpg1252\cocoartf1187\cocoasubrtf340
\cocoascreenfonts1{\fonttbl\f0\fswiss\fcharset0 Helvetica;}
{\colortbl;\red255\green255\blue255;}
\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc
\f0\fs20 \cf0 1: Request}</string>
<key>VerticalPad</key>
<integer>0</integer>
</dict>
<key>Wrap</key>
<string>NO</string>
</dict>
<dict>
<key>Bounds</key>
<string>{{430.83098347981803, 515.99999999999989}, {36, 14}}</string>
<key>Class</key>
<string>ShapedGraphic</string>
<key>FitText</key>
<string>YES</string>
<key>Flow</key>
<string>Resize</string>
<key>ID</key>
<integer>4026</integer>
<key>Shape</key>
<string>Rectangle</string>
<key>Style</key>
<dict>
<key>fill</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>shadow</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>stroke</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
</dict>
<key>Text</key>
<dict>
<key>Pad</key>
<integer>0</integer>
<key>Text</key>
<string>{\rtf1\ansi\ansicpg1252\cocoartf1187\cocoasubrtf340
\cocoascreenfonts1{\fonttbl\f0\fswiss\fcharset0 Helvetica;}
{\colortbl;\red255\green255\blue255;}
\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc
\f0\fs24 \cf0 Server}</string>
<key>VerticalPad</key>
<integer>0</integer>
</dict>
<key>Wrap</key>
<string>NO</string>
</dict>
<dict>
<key>Bounds</key>
<string>{{40.499999999999993, 486.66666666666663}, {31, 14}}</string>
<key>Class</key>
<string>ShapedGraphic</string>
<key>FitText</key>
<string>YES</string>
<key>Flow</key>
<string>Resize</string>
<key>ID</key>
<integer>4025</integer>
<key>Shape</key>
<string>Rectangle</string>
<key>Style</key>
<dict>
<key>fill</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>shadow</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>stroke</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
</dict>
<key>Text</key>
<dict>
<key>Pad</key>
<integer>0</integer>
<key>Text</key>
<string>{\rtf1\ansi\ansicpg1252\cocoartf1187\cocoasubrtf340
\cocoascreenfonts1{\fonttbl\f0\fswiss\fcharset0 Helvetica;}
{\colortbl;\red255\green255\blue255;}
\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc
\f0\fs24 \cf0 Client}</string>
<key>VerticalPad</key>
<integer>0</integer>
</dict>
<key>Wrap</key>
<string>NO</string>
</dict>
<dict>
<key>Bounds</key>
<string>{{417.16432189941418, 323.90565299479198}, {63.333332061767578, 185.52200317382812}}</string>
<key>Class</key>
<string>ShapedGraphic</string>
<key>ID</key>
<integer>4004</integer>
<key>ImageID</key>
<integer>6</integer>
<key>Shape</key>
<string>Rectangle</string>
<key>Style</key>
<dict>
<key>fill</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>shadow</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>stroke</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
</dict>
</dict>
<dict>
<key>Bounds</key>
<string>{{205.34386889139773, 289.33333333333331}, {84, 248.66667175292969}}</string>
<key>Class</key>
<string>ShapedGraphic</string>
<key>ID</key>
<integer>4023</integer>
<key>Shape</key>
<string>Rectangle</string>
<key>Style</key>
<dict>
<key>fill</key>
<dict>
<key>Color</key>
<dict>
<key>b</key>
<string>0</string>
<key>g</key>
<string>0.463735</string>
<key>r</key>
<string>1</string>
</dict>
</dict>
</dict>
<key>Text</key>
<dict>
<key>Text</key>
<string>{\rtf1\ansi\ansicpg1252\cocoartf1187\cocoasubrtf340
\cocoascreenfonts1{\fonttbl\f0\fswiss\fcharset0 Helvetica;}
{\colortbl;\red255\green255\blue255;\red37\green17\blue0;}
\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc
\f0\fs24 \cf2 mitmproxy}</string>
</dict>
</dict>
<dict>
<key>Bounds</key>
<string>{{4.6666666467984399, 351.33332316080771}, {102.66666412353516, 130.66667175292969}}</string>
<key>Class</key>
<string>ShapedGraphic</string>
<key>ID</key>
<integer>134</integer>
<key>ImageID</key>
<integer>3</integer>
<key>Shape</key>
<string>Rectangle</string>
<key>Style</key>
<dict>
<key>fill</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>shadow</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>stroke</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
</dict>
</dict>
</array>
<key>GridInfo</key>
<dict/>
<key>GuidesLocked</key>
<string>NO</string>
<key>GuidesVisible</key>
<string>YES</string>
<key>HPages</key>
<integer>1</integer>
<key>ImageCounter</key>
<integer>7</integer>
<key>ImageLinkBack</key>
<array>
<dict/>
<dict/>
</array>
<key>ImageList</key>
<array>
<string>image6.tiff</string>
<string>image3.icns</string>
</array>
<key>KeepToScale</key>
<false/>
<key>Layers</key>
<array>
<dict>
<key>Lock</key>
<string>NO</string>
<key>Name</key>
<string>Layer 1</string>
<key>Print</key>
<string>YES</string>
<key>View</key>
<string>YES</string>
</dict>
</array>
<key>LayoutInfo</key>
<dict>
<key>Animate</key>
<string>NO</string>
<key>circoMinDist</key>
<real>18</real>
<key>circoSeparation</key>
<real>0.0</real>
<key>layoutEngine</key>
<string>dot</string>
<key>neatoSeparation</key>
<real>0.0</real>
<key>twopiSeparation</key>
<real>0.0</real>
</dict>
<key>LinksVisible</key>
<string>NO</string>
<key>MagnetsVisible</key>
<string>NO</string>
<key>MasterSheets</key>
<array/>
<key>ModificationDate</key>
<string>2013-01-03 02:27:49 +0000</string>
<key>Modifier</key>
<string>Aldo Cortesi</string>
<key>NotesVisible</key>
<string>NO</string>
<key>Orientation</key>
<integer>2</integer>
<key>OriginVisible</key>
<string>NO</string>
<key>PageBreaks</key>
<string>YES</string>
<key>PrintInfo</key>
<dict>
<key>NSBottomMargin</key>
<array>
<string>float</string>
<string>41</string>
</array>
<key>NSHorizonalPagination</key>
<array>
<string>coded</string>
<string>BAtzdHJlYW10eXBlZIHoA4QBQISEhAhOU051bWJlcgCEhAdOU1ZhbHVlAISECE5TT2JqZWN0AIWEASqEhAFxlwCG</string>
</array>
<key>NSLeftMargin</key>
<array>
<string>float</string>
<string>18</string>
</array>
<key>NSPaperSize</key>
<array>
<string>size</string>
<string>{595.19998741149902, 841.79998779296875}</string>
</array>
<key>NSPrintReverseOrientation</key>
<array>
<string>int</string>
<string>0</string>
</array>
<key>NSRightMargin</key>
<array>
<string>float</string>
<string>18</string>
</array>
<key>NSTopMargin</key>
<array>
<string>float</string>
<string>18</string>
</array>
</dict>
<key>PrintOnePage</key>
<false/>
<key>ReadOnly</key>
<string>NO</string>
<key>RowAlign</key>
<integer>1</integer>
<key>RowSpacing</key>
<real>36</real>
<key>SheetTitle</key>
<string>Canvas 1</string>
<key>SmartAlignmentGuidesActive</key>
<string>YES</string>
<key>SmartDistanceGuidesActive</key>
<string>YES</string>
<key>UniqueID</key>
<integer>1</integer>
<key>UseEntirePage</key>
<false/>
<key>VPages</key>
<integer>1</integer>
<key>WindowInfo</key>
<dict>
<key>CurrentSheet</key>
<integer>0</integer>
<key>ExpandedCanvases</key>
<array>
<dict>
<key>name</key>
<string>Canvas 1</string>
</dict>
</array>
<key>Frame</key>
<string>{{300, 236}, {974, 874}}</string>
<key>ListView</key>
<true/>
<key>OutlineWidth</key>
<integer>142</integer>
<key>RightSidebar</key>
<false/>
<key>ShowRuler</key>
<true/>
<key>Sidebar</key>
<true/>
<key>SidebarWidth</key>
<integer>120</integer>
<key>VisibleRegion</key>
<string>{{0, 202}, {550, 469.33333333333337}}</string>
<key>Zoom</key>
<real>1.5</real>
<key>ZoomValues</key>
<array>
<array>
<string>Canvas 1</string>
<real>1.5</real>
<real>1</real>
</array>
</array>
</dict>
</dict>
</plist>

Binary file not shown.

Binary file not shown.

File diff suppressed because it is too large Load Diff

Binary file not shown.

Binary file not shown.

View File

@ -1,30 +1,80 @@
<div id="doc">
<div style="" id="hd" class="doc">
<!--(block nav)-->
<div id="nav">
<!--(block pb)-->
<a href="@!urlTo(previous)!@">prev</a>
<!--(end)-->
<!--(block nb)-->
<a href="@!urlTo(next)!@">next</a>
<!--(end)-->
$!pb if previous else "prev"!$ |
<a href="@!urlTo('/index.html')!@">index</a> |
$!nb if next else "next"!$
</div>
<!--(end)-->
$!nav if this.title!="docs" else ""!$
<h1><a href="@!urlTo("/index.html")!@">mitmproxy 0.9 docs</a></h1>
</div>
<div id="bd">
<div id="yui-main">
<div style="" class="yui-b">
$!title if this.title!="docs" else ""!$
$!body!$
</div>
</div>
</div>
<div style="" id="ft" class="doc">
<p>@!copyright!@</p>
<div class="navbar">
<div class="navbar-inner">
<div class="container-fluid">
<a class="btn btn-navbar" data-toggle="collapse" data-target=".nav-collapse">
<span class="icon-bar"></span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
</a>
<a class="brand" href="@!urlTo("/index.html")!@">mitmproxy 0.9 docs</a>
</div><!--/.nav-collapse -->
</div>
</div>
</div>
<div class="container-fluid">
<div class="row-fluid">
<div class="span3">
<div class="well sidebar-nav">
<ul class="nav nav-list">
$!nav("index.html", this, state)!$
$!nav("install.html", this, state)!$
$!nav("howmitmproxy.html", this, state)!$
$!nav("faq.html", this, state)!$
<li class="nav-header">Tools</li>
$!nav("mitmproxy.html", this, state)!$
$!nav("mitmdump.html", this, state)!$
<li class="nav-header">Features</li>
$!nav("anticache.html", this, state)!$
$!nav("clientreplay.html", this, state)!$
$!nav("filters.html", this, state)!$
$!nav("proxyauth.html", this, state)!$
$!nav("replacements.html", this, state)!$
$!nav("serverreplay.html", this, state)!$
$!nav("setheaders.html", this, state)!$
$!nav("sticky.html", this, state)!$
$!nav("reverseproxy.html", this, state)!$
$!nav("upstreamcerts.html", this, state)!$
<li class="nav-header">SSL interception</li>
$!nav("ssl.html", this, state)!$
$!nav("certinstall/firefox.html", this, state)!$
$!nav("certinstall/osx.html", this, state)!$
$!nav("certinstall/windows7.html", this, state)!$
$!nav("certinstall/ios.html", this, state)!$
$!nav("certinstall/android.html", this, state)!$
<li class="nav-header">Transparent Proxying</li>
$!nav("transparent.html", this, state)!$
$!nav("transparent/linux.html", this, state)!$
$!nav("transparent/osx.html", this, state)!$
<li class="nav-header">Tutorials</li>
$!nav("tutorials/30second.html", this, state)!$
$!nav("tutorials/gamecenter.html", this, state)!$
<li class="nav-header">Scripting mitmproxy</li>
$!nav("scripting/inlinescripts.html", this, state)!$
$!nav("scripting/libmproxy.html", this, state)!$
</ul>
</div>
</div>
<div class="span9">
<div class="page-header">
<h1>@!this.title!@</h1>
</div>
$!body!$
</div>
</div><!--/row-->
<hr>
<footer>
<p>@!copyright!@</p>
</footer>
</div><!--/.fluid-container-->

View File

@ -0,0 +1,771 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>ActiveLayerIndex</key>
<integer>0</integer>
<key>ApplicationVersion</key>
<array>
<string>com.omnigroup.OmniGraffle.MacAppStore</string>
<string>139.16</string>
</array>
<key>AutoAdjust</key>
<true/>
<key>BackgroundGraphic</key>
<dict>
<key>Bounds</key>
<string>{{0, 0}, {559.19998741149902, 782.79998779296875}}</string>
<key>Class</key>
<string>SolidGraphic</string>
<key>ID</key>
<integer>2</integer>
<key>Style</key>
<dict>
<key>shadow</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>stroke</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
</dict>
</dict>
<key>BaseZoom</key>
<integer>0</integer>
<key>CanvasOrigin</key>
<string>{0, 0}</string>
<key>ColumnAlign</key>
<integer>1</integer>
<key>ColumnSpacing</key>
<real>36</real>
<key>CreationDate</key>
<string>2013-01-02 19:31:53 +0000</string>
<key>Creator</key>
<string>Aldo Cortesi</string>
<key>DisplayScale</key>
<string>1.000 cm = 1.000 cm</string>
<key>GraphDocumentVersion</key>
<integer>8</integer>
<key>GraphicsList</key>
<array>
<dict>
<key>Bounds</key>
<string>{{101.18773396809897, 358.41662979125977}, {62, 12}}</string>
<key>Class</key>
<string>ShapedGraphic</string>
<key>FitText</key>
<string>YES</string>
<key>Flow</key>
<string>Resize</string>
<key>FontInfo</key>
<dict>
<key>Font</key>
<string>Helvetica</string>
<key>Size</key>
<real>12</real>
</dict>
<key>ID</key>
<integer>4079</integer>
<key>Shape</key>
<string>Rectangle</string>
<key>Style</key>
<dict>
<key>fill</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>shadow</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>stroke</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
</dict>
<key>Text</key>
<dict>
<key>Pad</key>
<integer>0</integer>
<key>Text</key>
<string>{\rtf1\ansi\ansicpg1252\cocoartf1187\cocoasubrtf340
\cocoascreenfonts1{\fonttbl\f0\fswiss\fcharset0 Helvetica;}
{\colortbl;\red255\green255\blue255;}
\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc
\f0\fs20 \cf0 2: Redirection}</string>
<key>VerticalPad</key>
<integer>0</integer>
</dict>
<key>Wrap</key>
<string>NO</string>
</dict>
<dict>
<key>Bounds</key>
<string>{{102.18775939941409, 405.16666666666663}, {78, 12}}</string>
<key>Class</key>
<string>ShapedGraphic</string>
<key>FitText</key>
<string>YES</string>
<key>Flow</key>
<string>Resize</string>
<key>FontInfo</key>
<dict>
<key>Font</key>
<string>Helvetica</string>
<key>Size</key>
<real>12</real>
</dict>
<key>ID</key>
<integer>4078</integer>
<key>Shape</key>
<string>Rectangle</string>
<key>Style</key>
<dict>
<key>fill</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>shadow</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>stroke</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
</dict>
<key>Text</key>
<dict>
<key>Pad</key>
<integer>0</integer>
<key>Text</key>
<string>{\rtf1\ansi\ansicpg1252\cocoartf1187\cocoasubrtf340
\cocoascreenfonts1{\fonttbl\f0\fswiss\fcharset0 Helvetica;}
{\colortbl;\red255\green255\blue255;}
\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc
\f0\fs20 \cf0 3: HTTP Request}</string>
<key>VerticalPad</key>
<integer>0</integer>
</dict>
<key>Wrap</key>
<string>NO</string>
</dict>
<dict>
<key>Class</key>
<string>LineGraphic</string>
<key>ControlPoints</key>
<array>
<string>{-29.333333333333343, 15.666671991348267}</string>
<string>{-14, -7.3333333333333712}</string>
</array>
<key>ID</key>
<integer>37</integer>
<key>Points</key>
<array>
<string>{196.99999491373691, 331.83332316080725}</string>
<string>{198.00000508626303, 402.49998982747394}</string>
</array>
<key>Style</key>
<dict>
<key>stroke</key>
<dict>
<key>Bezier</key>
<true/>
<key>HeadArrow</key>
<string>FilledArrow</string>
<key>Legacy</key>
<true/>
<key>LineType</key>
<integer>1</integer>
<key>TailArrow</key>
<string>0</string>
</dict>
</dict>
</dict>
<dict>
<key>Bounds</key>
<string>{{205.34387397766082, 289.3333333333328}, {84, 52.666667938232422}}</string>
<key>Class</key>
<string>ShapedGraphic</string>
<key>ID</key>
<integer>4076</integer>
<key>Shape</key>
<string>Rectangle</string>
<key>Style</key>
<dict>
<key>fill</key>
<dict>
<key>Color</key>
<dict>
<key>b</key>
<string>0.547829</string>
<key>g</key>
<string>1</string>
<key>r</key>
<string>0.790866</string>
</dict>
</dict>
</dict>
<key>Text</key>
<dict>
<key>Text</key>
<string>{\rtf1\ansi\ansicpg1252\cocoartf1187\cocoasubrtf340
\cocoascreenfonts1{\fonttbl\f0\fswiss\fcharset0 Helvetica;}
{\colortbl;\red255\green255\blue255;\red37\green17\blue0;}
\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc
\f0\fs24 \cf2 router}</string>
</dict>
</dict>
<dict>
<key>Class</key>
<string>LineGraphic</string>
<key>ID</key>
<integer>4075</integer>
<key>Points</key>
<array>
<string>{304.061024983724, 422.16667167345679}</string>
<string>{348.49764506022132, 422.16667167345696}</string>
<string>{365.83097839355469, 421.50000500679027}</string>
<string>{417.16433715820312, 421.16667175292963}</string>
</array>
<key>Style</key>
<dict>
<key>stroke</key>
<dict>
<key>HeadArrow</key>
<string>FilledArrow</string>
<key>Legacy</key>
<true/>
<key>TailArrow</key>
<string>0</string>
</dict>
</dict>
</dict>
<dict>
<key>Bounds</key>
<string>{{321.11267089843761, 405.16706339518225}, {49, 12}}</string>
<key>Class</key>
<string>ShapedGraphic</string>
<key>FitText</key>
<string>YES</string>
<key>Flow</key>
<string>Resize</string>
<key>FontInfo</key>
<dict>
<key>Font</key>
<string>Helvetica</string>
<key>Size</key>
<real>12</real>
</dict>
<key>ID</key>
<integer>4067</integer>
<key>Shape</key>
<string>Rectangle</string>
<key>Style</key>
<dict>
<key>fill</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>shadow</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>stroke</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
</dict>
<key>Text</key>
<dict>
<key>Pad</key>
<integer>0</integer>
<key>Text</key>
<string>{\rtf1\ansi\ansicpg1252\cocoartf1187\cocoasubrtf340
\cocoascreenfonts1{\fonttbl\f0\fswiss\fcharset0 Helvetica;}
{\colortbl;\red255\green255\blue255;}
\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc
\f0\fs20 \cf0 4: Request}</string>
<key>VerticalPad</key>
<integer>0</integer>
</dict>
<key>Wrap</key>
<string>NO</string>
</dict>
<dict>
<key>Bounds</key>
<string>{{101.18773682912195, 295.66660690307623}, {62, 12}}</string>
<key>Class</key>
<string>ShapedGraphic</string>
<key>FitText</key>
<string>YES</string>
<key>Flow</key>
<string>Resize</string>
<key>FontInfo</key>
<dict>
<key>Font</key>
<string>Helvetica</string>
<key>Size</key>
<real>12</real>
</dict>
<key>ID</key>
<integer>4058</integer>
<key>Shape</key>
<string>Rectangle</string>
<key>Style</key>
<dict>
<key>fill</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>shadow</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>stroke</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
</dict>
<key>Text</key>
<dict>
<key>Pad</key>
<integer>0</integer>
<key>Text</key>
<string>{\rtf1\ansi\ansicpg1252\cocoartf1187\cocoasubrtf340
\cocoascreenfonts1{\fonttbl\f0\fswiss\fcharset0 Helvetica;}
{\colortbl;\red255\green255\blue255;}
\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc
\f0\fs20 \cf0 1: Connection}</string>
<key>VerticalPad</key>
<integer>0</integer>
</dict>
<key>Wrap</key>
<string>NO</string>
</dict>
<dict>
<key>Class</key>
<string>LineGraphic</string>
<key>ID</key>
<integer>4041</integer>
<key>Points</key>
<array>
<string>{85.896713256836037, 421.41666793823208}</string>
<string>{199.00002034505209, 421.16666666666669}</string>
</array>
<key>Style</key>
<dict>
<key>stroke</key>
<dict>
<key>HeadArrow</key>
<string>FilledArrow</string>
<key>Legacy</key>
<true/>
<key>TailArrow</key>
<string>0</string>
</dict>
</dict>
</dict>
<dict>
<key>Class</key>
<string>LineGraphic</string>
<key>ID</key>
<integer>31</integer>
<key>Points</key>
<array>
<string>{84.896687825520857, 314.66666126251221}</string>
<string>{129.33330790201822, 314.66666126251238}</string>
<string>{146.66664123535153, 313.99999459584569}</string>
<string>{198, 313.66666134198505}</string>
</array>
<key>Style</key>
<dict>
<key>stroke</key>
<dict>
<key>HeadArrow</key>
<string>FilledArrow</string>
<key>Legacy</key>
<true/>
<key>TailArrow</key>
<string>0</string>
</dict>
</dict>
</dict>
<dict>
<key>Bounds</key>
<string>{{430.83098347981803, 515.99999999999989}, {36, 14}}</string>
<key>Class</key>
<string>ShapedGraphic</string>
<key>FitText</key>
<string>YES</string>
<key>Flow</key>
<string>Resize</string>
<key>ID</key>
<integer>4026</integer>
<key>Shape</key>
<string>Rectangle</string>
<key>Style</key>
<dict>
<key>fill</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>shadow</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>stroke</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
</dict>
<key>Text</key>
<dict>
<key>Pad</key>
<integer>0</integer>
<key>Text</key>
<string>{\rtf1\ansi\ansicpg1252\cocoartf1187\cocoasubrtf340
\cocoascreenfonts1{\fonttbl\f0\fswiss\fcharset0 Helvetica;}
{\colortbl;\red255\green255\blue255;}
\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc
\f0\fs24 \cf0 Server}</string>
<key>VerticalPad</key>
<integer>0</integer>
</dict>
<key>Wrap</key>
<string>NO</string>
</dict>
<dict>
<key>Bounds</key>
<string>{{40.499999999999993, 486.66666666666663}, {31, 14}}</string>
<key>Class</key>
<string>ShapedGraphic</string>
<key>FitText</key>
<string>YES</string>
<key>Flow</key>
<string>Resize</string>
<key>ID</key>
<integer>4025</integer>
<key>Shape</key>
<string>Rectangle</string>
<key>Style</key>
<dict>
<key>fill</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>shadow</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>stroke</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
</dict>
<key>Text</key>
<dict>
<key>Pad</key>
<integer>0</integer>
<key>Text</key>
<string>{\rtf1\ansi\ansicpg1252\cocoartf1187\cocoasubrtf340
\cocoascreenfonts1{\fonttbl\f0\fswiss\fcharset0 Helvetica;}
{\colortbl;\red255\green255\blue255;}
\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc
\f0\fs24 \cf0 Client}</string>
<key>VerticalPad</key>
<integer>0</integer>
</dict>
<key>Wrap</key>
<string>NO</string>
</dict>
<dict>
<key>Bounds</key>
<string>{{417.16432189941418, 323.90565299479198}, {63.333332061767578, 185.52200317382812}}</string>
<key>Class</key>
<string>ShapedGraphic</string>
<key>ID</key>
<integer>4004</integer>
<key>ImageID</key>
<integer>6</integer>
<key>Shape</key>
<string>Rectangle</string>
<key>Style</key>
<dict>
<key>fill</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>shadow</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>stroke</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
</dict>
</dict>
<dict>
<key>Bounds</key>
<string>{{205.34386889139773, 289.33333333333331}, {84, 248.66667175292969}}</string>
<key>Class</key>
<string>ShapedGraphic</string>
<key>ID</key>
<integer>4023</integer>
<key>Shape</key>
<string>Rectangle</string>
<key>Style</key>
<dict>
<key>fill</key>
<dict>
<key>Color</key>
<dict>
<key>b</key>
<string>0</string>
<key>g</key>
<string>0.463735</string>
<key>r</key>
<string>1</string>
</dict>
</dict>
</dict>
<key>Text</key>
<dict>
<key>Text</key>
<string>{\rtf1\ansi\ansicpg1252\cocoartf1187\cocoasubrtf340
\cocoascreenfonts1{\fonttbl\f0\fswiss\fcharset0 Helvetica;}
{\colortbl;\red255\green255\blue255;\red37\green17\blue0;}
\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc
\f0\fs24 \cf2 mitmproxy}</string>
</dict>
</dict>
<dict>
<key>Bounds</key>
<string>{{4.6666666467984399, 351.33332316080771}, {102.66666412353516, 130.66667175292969}}</string>
<key>Class</key>
<string>ShapedGraphic</string>
<key>ID</key>
<integer>134</integer>
<key>ImageID</key>
<integer>3</integer>
<key>Shape</key>
<string>Rectangle</string>
<key>Style</key>
<dict>
<key>fill</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>shadow</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
<key>stroke</key>
<dict>
<key>Draws</key>
<string>NO</string>
</dict>
</dict>
</dict>
</array>
<key>GridInfo</key>
<dict/>
<key>GuidesLocked</key>
<string>NO</string>
<key>GuidesVisible</key>
<string>YES</string>
<key>HPages</key>
<integer>1</integer>
<key>ImageCounter</key>
<integer>7</integer>
<key>ImageLinkBack</key>
<array>
<dict/>
<dict/>
</array>
<key>ImageList</key>
<array>
<string>image6.tiff</string>
<string>image3.icns</string>
</array>
<key>KeepToScale</key>
<false/>
<key>Layers</key>
<array>
<dict>
<key>Lock</key>
<string>NO</string>
<key>Name</key>
<string>Layer 1</string>
<key>Print</key>
<string>YES</string>
<key>View</key>
<string>YES</string>
</dict>
</array>
<key>LayoutInfo</key>
<dict>
<key>Animate</key>
<string>NO</string>
<key>circoMinDist</key>
<real>18</real>
<key>circoSeparation</key>
<real>0.0</real>
<key>layoutEngine</key>
<string>dot</string>
<key>neatoSeparation</key>
<real>0.0</real>
<key>twopiSeparation</key>
<real>0.0</real>
</dict>
<key>LinksVisible</key>
<string>NO</string>
<key>MagnetsVisible</key>
<string>NO</string>
<key>MasterSheets</key>
<array/>
<key>ModificationDate</key>
<string>2013-01-03 04:13:10 +0000</string>
<key>Modifier</key>
<string>Aldo Cortesi</string>
<key>NotesVisible</key>
<string>NO</string>
<key>Orientation</key>
<integer>2</integer>
<key>OriginVisible</key>
<string>NO</string>
<key>PageBreaks</key>
<string>YES</string>
<key>PrintInfo</key>
<dict>
<key>NSBottomMargin</key>
<array>
<string>float</string>
<string>41</string>
</array>
<key>NSHorizonalPagination</key>
<array>
<string>coded</string>
<string>BAtzdHJlYW10eXBlZIHoA4QBQISEhAhOU051bWJlcgCEhAdOU1ZhbHVlAISECE5TT2JqZWN0AIWEASqEhAFxlwCG</string>
</array>
<key>NSLeftMargin</key>
<array>
<string>float</string>
<string>18</string>
</array>
<key>NSPaperSize</key>
<array>
<string>size</string>
<string>{595.19998741149902, 841.79998779296875}</string>
</array>
<key>NSPrintReverseOrientation</key>
<array>
<string>int</string>
<string>0</string>
</array>
<key>NSRightMargin</key>
<array>
<string>float</string>
<string>18</string>
</array>
<key>NSTopMargin</key>
<array>
<string>float</string>
<string>18</string>
</array>
</dict>
<key>PrintOnePage</key>
<false/>
<key>ReadOnly</key>
<string>NO</string>
<key>RowAlign</key>
<integer>1</integer>
<key>RowSpacing</key>
<real>36</real>
<key>SheetTitle</key>
<string>Canvas 1</string>
<key>SmartAlignmentGuidesActive</key>
<string>YES</string>
<key>SmartDistanceGuidesActive</key>
<string>YES</string>
<key>UniqueID</key>
<integer>1</integer>
<key>UseEntirePage</key>
<false/>
<key>VPages</key>
<integer>1</integer>
<key>WindowInfo</key>
<dict>
<key>CurrentSheet</key>
<integer>0</integer>
<key>ExpandedCanvases</key>
<array>
<dict>
<key>name</key>
<string>Canvas 1</string>
</dict>
</array>
<key>Frame</key>
<string>{{295, 141}, {974, 874}}</string>
<key>ListView</key>
<true/>
<key>OutlineWidth</key>
<integer>142</integer>
<key>RightSidebar</key>
<false/>
<key>ShowRuler</key>
<true/>
<key>Sidebar</key>
<true/>
<key>SidebarWidth</key>
<integer>120</integer>
<key>VisibleRegion</key>
<string>{{0, 208}, {550, 469.33333333333337}}</string>
<key>Zoom</key>
<real>1.5</real>
<key>ZoomValues</key>
<array>
<array>
<string>Canvas 1</string>
<real>1.5</real>
<real>1</real>
</array>
</array>
</dict>
</dict>
</plist>

Binary file not shown.

Binary file not shown.

File diff suppressed because it is too large Load Diff

Binary file not shown.

Binary file not shown.

View File

@ -1,7 +0,0 @@
Please send any comments, suggestions and bug reports to <a href="mailto:$!docMaintainerEmail!$">$!docMaintainerEmail!$</a>.
__mitmproxy__ is licensed under Version 3 of the Gnu General Public License,
the full text of which can be found in the LICENSE file in the source
distribution.

View File

@ -1,10 +0,0 @@
- command-line: _--anticache_
- mitmproxy shortcut: _o_, then _a_
When the __anticache__ option is passed to mitmproxy, it removes headers
(__if-none-match__ and __if-modified-since__) that might elicit a
304-not-modified response from the server. This is useful when you want to make
sure you capture an HTTP exchange in its totality, and during [client
replay](@!urlTo("clientreplay.html")!@).

Binary file not shown.

Before

Width:  |  Height:  |  Size: 122 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 53 KiB

View File

@ -4,9 +4,9 @@ embarrasment](http://code.google.com/p/android/issues/detail?id=1273). It's
scarcely credible, but Android didn't have a global proxy setting at all until
quite recently, and it's still not supported on many common Android versions.
In the meantime the app ecosystem has grown used to life without this basic
necessity, and many apps merrily ignore it even if it's there. The upshot is
that in many cases the only way to make interception work on Android is to do
it without relying on the proxy settings.
necessity, and many apps merrily ignore it even if it's there. This situation
is improving, but in many circumstances using [transparent
mode](@!urlTo("transparent.html")!@) is mandatory for testing Android apps.
We used an Asus Transformer Prime TF201 with Android 4.0.3 in the examples
below - your device may differ, but the broad process should be similar.
@ -16,7 +16,7 @@ Installing the mitmproxy certificate
====================================
The first step is to install mitmproxy's interception certificate on the
Android device. In your ~/.mitmproxy directory, there should be a file called
Android device. In your ~/.mitmproxy directory, there is a file called
__mitmproxy-ca-cert.cer__ - we need to transfer this file to
__/sdcard/Downloads__ on the Android device. If this file doesn't exist for
you, your certs were generated with an older version of mitmproxy - just copy
@ -51,53 +51,3 @@ settings, you're just about done - simply configure the settings to point at
mitmproxy. If not, proceed to the next step...
Working around Android's proxy shortcomings
===========================================
In response to Android's proxy situation, a number of apps have been created to
duct-tape proxy support onto the OS. These tools work by running a rudimentary
local proxy on the device, and forwarding all traffic destined for HTTP/S ports
to it using iptables. Since the proxy is running locally, it can detect what
the final IP address of the redirected traffic would have been. The local proxy
then connects to a user-configured upstream proxy, and initiates a proxy
CONNECT request to the destination IP.
Now, if the configured upstream proxy is mitmproxy, we have a slight problem.
Proxy requests from the Android device in this scheme will specify only the
destination IP address, __not__ the destination domain. Mitmproxy needs the
target domain to generate a valid interception certificate. The solution is
mitmproxy's [upstream certificate](@!urlTo("upstreamcerts.html")!@) option.
When this is active, mitmproxy makes a connection to the upstream server to
obtain the certificate Common Name and Subject Alternative Names.
Adding all this together, we can achieve reliable Android interception with
only a few more minutes of setup. The instructions below show how to set up an
Android device with
[ProxyDroid](https://play.google.com/store/apps/details?id=org.proxydroid) (the
local "duct-tape" proxy implementation) to achieve interception.
Install ProxyDroid
------------------
First, root your device - this is required to install ProxyDroid. Then install
ProxyDroid from the Google Play store:
<img src="android-proxydroidinstall.png"/>
You will be prompted for super-user access, which you must allow. Next, enter
the ProxyDroid settings, and change the proxy settings to point to your
mitmproxy instance. When you're done, it should look something like this:
<img src="android-proxydroidsettings.png"/>
In this case, our mitmproxy instance is at the host __maru.otago.ac.nz__,
running on port __8080__.
When you start mitmproxy, make sure that the upstream certificate option is set
(use the _--upstream-cert_ command-line option, or enable it interactively
using the _o_ shortcut):
<pre class="terminal">
mitmproxy --upstream-cert
</pre>

BIN
doc-src/explicit.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 64 KiB

BIN
doc-src/explicit_https.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 77 KiB

View File

@ -0,0 +1,18 @@
When the __anticache__ option is passed to mitmproxy, it removes headers
(__if-none-match__ and __if-modified-since__) that might elicit a
304-not-modified response from the server. This is useful when you want to make
sure you capture an HTTP exchange in its totality. It's also often used during
[client replay](@!urlTo("clientreplay.html")!@), when you want to make sure the
server responds with complete data.
<table class="table">
<tbody>
<tr>
<th width="20%">command-line</th> <td>--anticache</td>
</tr>
<tr>
<th>mitmproxy shortcut</th> <td><b>o</b> then <b>a</b></td>
</tr>
</tbody>
</table>

View File

@ -1,7 +1,4 @@
- command-line: _-c path_
- mitmproxy shortcut: _c_
Client-side replay does what it says on the tin: you provide a previously saved
HTTP conversation, and mitmproxy replays the client requests one by one. Note
that mitmproxy serializes the requests, waiting for a response from the server
@ -9,6 +6,17 @@ before starting the next request. This might differ from the recorded
conversation, where requests may have been made concurrently.
You may want to use client-side replay in conjunction with the
[anticache](@!urlTo("anticache.html")!@) option.
[anticache](@!urlTo("anticache.html")!@) option, to make sure the server
responds with complete data.
<table class="table">
<tbody>
<tr>
<th width="20%">command-line</th> <td>-c path</td>
</tr>
<tr>
<th>mitmproxy shortcut</th> <td><b>c</b></td>
</tr>
</tbody>
</table>

View File

@ -2,13 +2,15 @@
Many commands in __mitmproxy__ and __mitmdump__ take a filter expression.
Filter expressions consist of the following operators:
<table>
<table class="table">
<tbody>
<!--(for i in filt_help)-->
<tr>
<td class="filt_cmd">@!i[0]!@</td>
<td class="filt_help">@!i[1]!@</td>
</tr>
<!--(end)-->
</tbody>
</table>
- Regexes are Python-style

14
doc-src/features/index.py Normal file
View File

@ -0,0 +1,14 @@
from countershape import Page
pages = [
Page("anticache.html", "Anticache"),
Page("clientreplay.html", "Client-side replay"),
Page("filters.html", "Filter expressions"),
Page("setheaders.html", "Set Headers"),
Page("serverreplay.html", "Server-side replay"),
Page("sticky.html", "Sticky cookies and auth"),
Page("proxyauth.html", "Proxy Authentication"),
Page("replacements.html", "Replacements"),
Page("reverseproxy.html", "Reverse proxy mode"),
Page("upstreamcerts.html", "Upstream Certs"),
]

View File

@ -0,0 +1,25 @@
Asks the user for authentication before they are permitted to use the proxy.
Authentication headers are stripped from the flows, so they are not passed to
upstream servers. For now, only HTTP Basic authentication is supported.
<table class="table">
<tbody>
<tr>
<th width="20%">command-line</th>
<td>
<ul>
<li>--nonanonymous</li>
<li>--singleuser USER</li>
<li>--htpasswd PATH</li>
</ul>
</td>
</tr>
</tbody>
</table>

View File

@ -1,6 +1,3 @@
- command-line: _--replace_, _--replace-from-file_
- mitmproxy shortcut: _R_
Mitmproxy lets you specify an arbitrary number of patterns that define text
replacements within flows. Each pattern has 3 components: a filter that defines
which flows a replacement applies to, a regular expression that defines what
@ -59,3 +56,19 @@ The _R_ shortcut key in mitmproxy lets you add and edit replacement hooks using
a built-in editor. The context-sensitive help (_h_) has complete usage
information.
<table class="table">
<tbody>
<tr>
<th width="20%">command-line</th>
<td>
<ul>
<li>--replace</li>
<li>--replace-from-file</li>
</ul>
</td>
</tr>
<tr>
<th>mitmproxy shortcut</th> <td><b>R</b></td>
</tr>
</tbody>
</table>

View File

@ -1,8 +1,17 @@
- command-line: _-P_ http[s]://hostname[:port]
- mitmproxy shortcut: _P_
In reverse proxy mode, mitmproxy acts as a standard HTTP server and forwards
all requests to the specified upstream server. Note that the displayed URL for
flows in this mode will use the value of the __Host__ header field from the
request, not the reverse proxy server.
<table class="table">
<tbody>
<tr>
<th width="20%">command-line</th> <td>-P http[s]://hostname[:port]</td>
</tr>
<tr>
<th>mitmproxy shortcut</th> <td><b>P</b></td>
</tr>
</tbody>
</table>

View File

@ -0,0 +1,18 @@
This feature lets you specify a set of headers to be added to requests or
responses, based on a filter pattern. You can specify these either on the
command-line, or through an interactive editor in mitmproxy.
<table class="table">
<tbody>
<tr>
<th width="20%">command-line</th>
<td>
--setheader PATTERN
</td>
</tr>
<tr>
<th>mitmproxy shortcut</th> <td><b>H</b></td>
</tr>
</tbody>
</table>

View File

@ -1,10 +1,6 @@
## Sticky cookies
- command-line: _-t_ (sticky cookies on all requests)
- command-line: _-T filt_ (sticky cookies on requests matching filt)
- mitmproxy shortcut: _t_
When the sticky cookie option is set, __mitmproxy__ will add the cookie most
recently set by the server to any cookie-less request. Consider a service that
sets a cookie to track the session after authentication. Using sticky cookies,
@ -20,15 +16,47 @@ replay](@!urlTo("clientreplay.html")!@) - you can record the authentication
process once, and simply replay it on startup every time you need to interact
with the secured resources.
<table class="table">
<tbody>
<tr>
<th width="20%">command-line</th>
<td>
<ul>
<li>-t (sticky cookies on all requests)</li>
<li>-T FILTER (sticky cookies on requests matching filter</li>
</ul>
</td>
</tr>
<tr>
<th>mitmproxy shortcut</th> <td><b>t</b></td>
</tr>
</tbody>
</table>
## Sticky auth
- command-line: _-u_ (sticky auth on all requests)
- command-line: _-U filt_ (sticky auth on requests matching filt)
- mitmproxy shortcut: _u_
The sticky auth option is analogous to the sticky cookie option, in that HTTP
__Authorization__ headers are simply replayed to the server once they have been
seen. This is enough to allow you to access a server resource using HTTP Basic
authentication through the proxy. Note that __mitmproxy__ doesn't (yet) support
replay of HTTP Digest authentication.
<table class="table">
<tbody>
<tr>
<th width="20%">command-line</th>
<td>
<ul>
<li>-u (sticky auth on all requests)</li>
<li>-U FILTER (sticky auth on requests matching filter</li>
</ul>
</td>
</tr>
<tr>
<th>mitmproxy shortcut</th> <td><b>u</b></td>
</tr>
</tbody>
</table>

View File

@ -0,0 +1,21 @@
When mitmproxy receives a connection destined for an SSL-protected service, it
freezes the connection before reading its request data, and makes a connection
to the upstream server to "sniff" the contents of its SSL certificate. The
information gained - the __Common Name__ and __Subject Alternative Names__ - is
then used to generate the interception certificate, which is sent to the client
so the connection can continue.
This rather intricate little dance lets us seamlessly generate correct
certificates even if the client has specifed only an IP address rather than the
hostname. It also means that we don't need to sniff additional data to generate
certs in transparent mode.
Upstream cert sniffing is on by default, and can optionally be turned off.
<table class="table">
<tbody>
<tr>
<th width="20%">command-line</th> <td>--no-upstream-cert</td>
</tr>
</tbody>
</table>

341
doc-src/howmitmproxy.html Normal file
View File

@ -0,0 +1,341 @@
TODO:
- Clarify terminology: SSL vs TLS
Mitmproxy is an enormously flexible tool. Knowing exactly how the proxying
process works will help you deploy it more creatively, and let you understand
its fundamental assumptions and how to work around them. This document explains
mitmproxy's proxy mechanism by example, starting with the simplest explicit
proxy configuration, and working up to the most complicated interaction -
transparent proxying of SSL-protected traffic in the presence of SNI.
<div class="page-header">
<h1>Explicit HTTP</h1>
</div>
Configuring the client to use mitmproxy as an explicit proxy is the simplest
and most reliable way to intercept traffic. The proxy protocol is codified in
the [HTTP RFC](http://www.ietf.org/rfc/rfc2068.txt), so the behaviour of both
the client and the server is well defined, and usually reliable. In the
simplest possible interaction with mitmproxy, a client connects directly to the
proxy, and makes a request that looks like this:
<pre>GET http://example.com/index.html HTTP/1.1</pre>
This is a proxy GET request - an extended form of the vanilla HTTP GET request
that includes a schema and host specification, and it includes all the
information mitmproxy needs to proceed.
<img src="explicit.png"/>
<table class="table">
<tbody>
<tr>
<td><b>1</b></td>
<td>The client connects to the proxy and makes a request.</td>
</tr>
<tr>
<td><b>2</b></td>
<td>Mitmproxy connects to the upstream server and simply forwards
the request on.</td>
</tr>
</tbody>
</table>
<div class="page-header">
<h1>Explicit HTTPS</h1>
</div>
The process for an explicitly proxied HTTPS connection is quite different. The
client connects to the proxy and makes a request that looks like this:
<pre>CONNECT example.com:443 HTTP/1.1</pre>
A conventional proxy can neither view nor manipulate an SSL-encrypted data
stream, so a CONNECT request simply asks the proxy to open a pipe between the
client and server. The proxy here is just a facilitator - it blindly forwards
data in both directions without knowing anything about the contents. The
negotiation of the SSL connection happens over this pipe, and the subsequent
flow of requests and responses are completely opaque to the proxy.
## The MITM in mitmproxy
This is where mitmproxy's fundamental trick comes in to play. The MITM in its
name stands for Man-In-The-Middle - a reference to the process we use to
intercept and interfere with these theoretially opaque data streams. The basic
idea is to pretend to be the server to the client, and pretend to be the client
to the server. The tricky part is that the Certificate Authority system is
designed to prevent exactly this attack, by allowing a trusted third-party to
cryptographically sign a server's SSL certificates to verify that the certs are
legit. If this signature is from a non-trusted party, a secure client will
simply drop the connection and refuse to proceed. Despite the many shortcomings
of the CA system as it exists today, this is usually fatal to attempts to MITM
an SSL connection for analysis.
Our answer to this conundrum is to become a trusted Certificate Authority
ourselves. Mitmproxy includes a full CA implementation that generates
interception certificates on the fly. To get the client to trust these
certificates, we register mitmproxy as a CA with the device manually.
## Complication 1: What's the remote hostname?
To proceed with this plan, we need to know the domain name to use in the
interception certificate - the client will verify that the certificate is for
the domain it's connecting to, and abort if this is not the case. At first
blush, it seems that the CONNECT request above gives us all we need - in this
example, both of these values are "example.com". But what if the client had
initiated the connection as follows:
<pre>CONNECT 10.1.1.1:443 HTTP/1.1</pre>
Using the IP address is perfectly legitimate because it gives us enough
information to initiate the pipe, even though it doesn't reveal the remote
hostname.
Mitmproxy has a cunning mechanism that smooths this over - upstream certificate
sniffing. As soon as we see the CONNECT request, we pause the client part of
the conversation, and initiate a simultaneous connection to the server. We
complete the SSL handshake with the server, and inspect the certificates it
used. Now, we use the Common Name in the upstream SSL certificates to generate
the dummy certificate for the client. Voila, we have the correct hostname to
present to the client, even if it was never specified.
## Complication 2: Subject Alternate Name
Enter the next complication. Sometimes, the certificate Common Name is not, in
fact, the hostname that the client is connecting to. This is because of the
optional Subject Alternate Name field in the SSL certificate that allows an
arbitrary number of alternate domains to be specified. If the expected domain
matches any of these, the client wil proceed, even though the domain doesn't
match the certificate Common Name. The answer here is simple: when extract the
CN from the upstream cert, we also extract the SANs, and add them to the
generated dummy certificate.
## Complication 3: Server Name Indication
One of the big limitations of conventional SSL is that each certificate
requires its own IP address. This means that you couldn't do virtual hosting
where multiple domains with independent certificates share the same IP address.
In a world with a rapidly shrinking IPv4 address pool this is a problem, and we
have a solution in the form of the Server Name Indication extension to the SSL
and TLS protocols. This lets the client specify the remote server name at the
start of the SSL handshake, which then lets the server select the right
certificate to complete the process.
SNI breaks our upstream certificate sniffing process, because when we connect
without using SNI, we get served a default certificate that may have nothing to
do with the certificate expected by the client. The solution is another tricky
complication to the client connection process. After the client connects, we
allow the SSL handshake to continue until just _after_ the SNI value has been
passed to us. Now we can pause the conversation, and initiate an upstream
connection using the correct SNI value, which then serves us the correct
upstream certificate, from which we can extract the expected CN and SANs.
## Putting it all together
Lets put all of this together into the complete explicitly proxied HTTPS flow.
<img src="explicit_https.png"/>
<table class="table">
<tbody>
<tr>
<td><b>1</b></td>
<td>The client makes a connection to mitmproxy, and issues an HTTP
CONNECT request.</td>
</tr>
<tr>
<td><b>2</b></td>
<td>Mitmproxy responds with a 200 Connection Established, as if it
has set up the CONNECT pipe.</td>
</tr>
<tr>
<td><b>3</b></td>
<td>The client believes it's talking to the remote server, and
initiates the SSL connection. It uses SNI to indicate the hostname
it is connecting to.</td>
</tr>
<tr>
<td><b>4</b></td>
<td>Mitmproxy connects to the server, and establishes an SSL
connection using the SNI hostname indicated by the client.</td>
</tr>
<tr>
<td><b>5</b></td>
<td>The server responds with the matching SSL certificate, which
contains the CN and SAN values needed to generate the interception
certificate.</td>
</tr>
<tr>
<td><b>6</b></td>
<td>Mitmproxy generates the interception cert, and continues the
client SSL handshake paused in step 3.</td>
</tr>
<tr>
<td><b>7</b></td>
<td>The client sends the request over the established SSL
connection.</td>
</tr>
<tr>
<td><b>7</b></td>
<td>Mitmproxy passes the request on to the server over the SSL
connection initiated in step 4.</td>
</tr>
</tbody>
</table>
<div class="page-header">
<h1>Transparent HTTP</h1>
</div>
When a transparent proxy is used, the HTTP/S connection is redirected into a
proxy at the network layer, without any client configuration being required.
This makes transparent proxying ideal for those situations where you can't
change client behaviour - proxy-oblivious Android applications being a common
example.
To achieve this, we need to introduce two extra components. The first new
component is a router that transparently redirects the TCP connection to the
proxy. Once the client has initiated the connection, it makes a vanilla HTTP
request, which might look something like this:
<pre>GET /index.html HTTP/1.1</pre>
Note that this request differs from the explicit proxy variation, in that it
omits the scheme and hostname. How, then, do we know which upstream host to
forward the request to? The routing mechanism that has performed the
redirection keeps track of the original destination. Each different routing
mechanism has its own ideosyncratic way of exposing this data, so this
introduces the second component required for working transparent proxying: a
host module that knows how to retrieve the original destination address from
the router. Once we have this information, the process is fairly
straight-forward.
<img src="transparent.png"/>
<table class="table">
<tbody>
<tr>
<td><b>1</b></td>
<td>The client makes a connection to the server.</td>
</tr>
<tr>
<td><b>2</b></td>
<td>The router redirects the connection to mitmproxy, which is
typically listening on a local port of the same host. Mitmproxy
then consults the routing mechanism to establish what the original
destination was.</td>
</tr>
<tr>
<td><b>3</b></td>
<td>Now, we simply read the client's request...</td>
</tr>
<tr>
<td><b>4</b></td>
<td>... and forward it upstream.</td>
</tr>
</tbody>
</table>
<div class="page-header">
<h1>Transparent HTTPS</h1>
</div>
The process for transparently proxying an HTTPS request is a merger of the
methods we've outlined for transparently proxying HTTP, and explicitly proxying
HTTPS. We use the routing mechanism to establish the upstream server address,
and then proceed as for explit HTTPS connections to establish the CN and SANs,
and cope with SNI.
<img src="transparent_https.png"/>
<table class="table">
<tbody>
<tr>
<td><b>1</b></td>
<td>The client makes a connection to the server.</td>
</tr>
<tr>
<td><b>2</b></td>
<td>The router redirects the connection to mitmproxy, which is
typically listening on a local port of the same host. Mitmproxy
then consults the routing mechanism to establish what the original
destination was.</td>
</tr>
<tr>
<td><b>3</b></td>
<td>The client believes it's talking to the remote server, and
initiates the SSL connection. It uses SNI to indicate the hostname
it is connecting to.</td>
</tr>
<tr>
<td><b>4</b></td>
<td>Mitmproxy connects to the server, and establishes an SSL
connection using the SNI hostname indicated by the client.</td>
</tr>
<tr>
<td><b>5</b></td>
<td>The server responds with the matching SSL certificate, which
contains the CN and SAN values needed to generate the interception
certificate.</td>
</tr>
<tr>
<td><b>6</b></td>
<td>Mitmproxy generates the interception cert, and continues the
client SSL handshake paused in step 3.</td>
</tr>
<tr>
<td><b>7</b></td>
<td>The client sends the request over the established SSL
connection.</td>
</tr>
<tr>
<td><b>7</b></td>
<td>Mitmproxy passes the request on to the server over the SSL
connection initiated in step 4.</td>
</tr>
</tbody>
</table>

View File

@ -1,49 +1,4 @@
<ul class="docindex">
<li><a href="@!urlTo("intro.html")!@">Introduction</a></li>
<li><a href="@!urlTo("install.html")!@">Installation</a></li>
<li><a href="@!urlTo("mitmproxy.html")!@">mitmproxy</a></li>
<li><a href="@!urlTo("mitmdump.html")!@">mitmdump</a></li>
<li>Features
<ul>
<li><a href="@!urlTo("clientreplay.html")!@">Client-side replay</a></li>
<li><a href="@!urlTo("serverreplay.html")!@">Server-side replay</a></li>
<li><a href="@!urlTo("sticky.html")!@">Sticky cookies and auth</a></li>
<li><a href="@!urlTo("reverseproxy.html")!@">Reverse proxy mode</a></li>
<li><a href="@!urlTo("upstreamcerts.html")!@">Upstream Certs</a></li>
<li><a href="@!urlTo("replacements.html")!@">Replacements</a></li>
<li><a href="@!urlTo("anticache.html")!@">Anticache</a></li>
<li><a href="@!urlTo("filters.html")!@">Filter expressions</a></li>
</ul>
</li>
<li>Scripting mitmproxy
<ul>
<li><a href="@!urlTo("scripting/inlinescripts.html")!@">Inline Scripts</a></li>
<li><a href="@!urlTo("scripting/libmproxy.html")!@">libmproxy</a></li>
</ul>
</li>
<li><a href="@!urlTo("ssl.html")!@">Setting up SSL interception</a>
<ul>
<li><a href="@!urlTo("certinstall/firefox.html")!@">Firefox</a></li>
<li><a href="@!urlTo("certinstall/osx.html")!@">OSX</a></li>
<li><a href="@!urlTo("certinstall/windows7.html")!@">Windows 7</a></li>
<li><a href="@!urlTo("certinstall/ios.html")!@">iPhone/iPad</a></li>
<li><a href="@!urlTo("certinstall/android.html")!@">Android</a></li>
</ul>
</li>
<li><a href="@!urlTo("transparent.html")!@">Setting up Transparent Proxying</a>
<ul>
<li><a href="@!urlTo("transparent/linux.html")!@">Linux</a></li>
<li><a href="@!urlTo("transparent/osx.html")!@">OSX</a></li>
<li><a href="@!urlTo("transparent/osx.html")!@">OpenBSD</a></li>
</ul>
</li>
<li>Tutorials
<ul>
<li> <a href="@!urlTo("tutorials/30second.html")!@">Client replay: a 30 second example</a> </li>
<li> <a href="@!urlTo("tutorials/gamecenter.html")!@">Setting highscores on Apple's GameCenter</a> </li>
</ul>
</li>
<li><a href="@!urlTo("faq.html")!@">FAQ</a></li>
<li><a href="@!urlTo("admin.html")!@">Administrivia</a></li>
</ul>
@!index_contents!@

View File

@ -1,42 +1,29 @@
import os, sys
import countershape
from countershape import Page, Directory, PythonModule, markup
from countershape import Page, Directory, PythonModule, markup, model
import countershape.template
sys.path.insert(0, "..")
from libmproxy import filt
MITMPROXY_SRC = "~/git/public/mitmproxy"
if ns.options.website:
ns.title = countershape.template.Template(None, "<h1>@!this.title!@</h1>")
this.layout = countershape.Layout("_websitelayout.html")
else:
ns.title = countershape.template.Template(None, "<h1>@!this.title!@</h1>")
this.layout = countershape.Layout("_layout.html")
this.layout = countershape.Layout("_layout.html")
this.titlePrefix = "mitmproxy 0.9 - "
this.markup = markup.Markdown()
ns.docMaintainer = "Aldo Cortesi"
ns.docMaintainerEmail = "aldo@corte.si"
ns.copyright = u"\u00a9 mitmproxy project, 2012"
ns.index = countershape.widgets.SiblingPageIndex('/index.html', divclass="pageindex")
ns.copyright = u"\u00a9 mitmproxy project, 2013"
def mpath(p):
p = os.path.join(MITMPROXY_SRC, p)
return os.path.expanduser(p)
ns.license = file(mpath("LICENSE")).read()
ns.index_contents = file(mpath("README.mkd")).read()
top = os.path.abspath(os.getcwd())
def example(s):
d = file(mpath(s)).read()
extemp = """<div class="example">%s<div class="example_legend">(%s)</div></div>"""
return extemp%(countershape.template.Syntax("py")(d), s)
ns.example = example
filt_help = []
@ -64,25 +51,27 @@ filt_help.extend(
ns.filt_help = filt_help
def nav(page, current, state):
if current.match(page, False):
pre = '<li class="active">'
else:
pre = "<li>"
p = state.application.getPage(page)
return pre + '<a href="%s">%s</a></li>'%(model.UrlTo(page), p.title)
ns.nav = nav
pages = [
Page("index.html", "docs"),
Page("intro.html", "Introduction"),
Page("index.html", "Introduction"),
Page("install.html", "Installation"),
Page("mitmproxy.html", "mitmproxy"),
Page("mitmdump.html", "mitmdump"),
Page("clientreplay.html", "Client-side replay"),
Page("serverreplay.html", "Server-side replay"),
Page("sticky.html", "Sticky cookies and auth"),
Page("upstreamcerts.html", "Upstream Certs"),
Page("replacements.html", "Replacements"),
Page("reverseproxy.html", "Reverse proxy mode"),
Page("anticache.html", "Anticache"),
Page("filters.html", "Filter expressions"),
Page("ssl.html", "Setting up SSL interception"),
Page("howmitmproxy.html", "How mitmproxy works"),
Page("ssl.html", "Overview"),
Directory("certinstall"),
Directory("scripting"),
Directory("tutorials"),
Page("transparent.html", "Overview"),
Directory("transparent"),
Page("faq.html", "FAQ"),
Page("admin.html", "Administrivia")
]

View File

@ -1,54 +1,49 @@
## Using Pip
The preferred way to install mitmproxy - whether you're installing the latest
release or from source - is to use [pip](http://www.pip-installer.org/). If you
don't already have pip on your system, you can find installation instructions
[here](http://www.pip-installer.org/en/latest/installing.html).
The preferred way to install mitmproxy is to use
[pip](http://pypi.python.org/pypi/pip). A single command will install the
latest release of mitmproxy, along with all its dependencies:
<pre>
sudo pip install mitmproxy
## Installing the latest release
A single command will download and install the latest release of mitmproxy,
along with all its dependencies:
<pre class="terminal">
pip install mitmproxy
</pre>
## From Source
## Installing from source
- When installing from source, you will need to install the
[dependencies](@!urlTo("intro.html")!@) by hand.
- Then run the following command from the base of the source distribution:
When installing from source, the easiest method is still to use pip. In this
case run:
<pre>
sudo python setup.py install
<pre class="terminal">
pip install /path/to/source
</pre>
Note that if you're installing current git master, you will also have to
install the current git master of [netlib](http://github.com/cortesi/netlib) by
hand.
## OSX
- If you're running a Python interpreter installed with homebrew (or similar),
you may have to install some dependencies by hand.
- Make sure that XCode is installed from the App Store, and that the
command-line tools have been downloaded (XCode/Preferences/Downloads).
- Install __pip__ using the following command:
<pre>
sudo easy_install pip
</pre>
- Now use __pip__ to set up the dependencies and do the install:
<pre>
sudo pip install mitmproxy
</pre>
This procedure may vary if, for instance, you've installed Python from an
external source like [homebrew](http://mxcl.github.com/homebrew/). In that
case, the easiest way to proceed is to first install __easy_install__, then
continue as above.
- Now use __pip__ to do the installation, as above.
There are a few bits of customization you might want to do to make mitmproxy
comfortable to use. At the moment, mitmproxy's color scheme is optimized for a
dark background terminal, so you probably want to change the default. You can
use the OSX <b>open</b> program to create a simple and effective
<b>~/.mailcap</b> file to view HTTP bodies:
comfortable to use on OSX. The default color scheme is optimized for a dark
background terminal, but you can select a palette for a light terminal
background with the --palette option. You can use the OSX <b>open</b> program
to create a simple and effective <b>~/.mailcap</b> file to view request and
response bodies:
<pre>
<pre class="terminal">
application/*; /usr/bin/open -Wn %s
audio/*; /usr/bin/open -Wn %s
image/*; /usr/bin/open -Wn %s

View File

@ -1,4 +0,0 @@
@!index_contents!@

View File

@ -1,4 +1,3 @@
__mitmproxy__ has a powerful scripting API that allows you to modify flows
on-the-fly or rewrite previously saved flows locally.
@ -22,13 +21,13 @@ response itself.
Called once on startup, before any other events.
###clientconnect(ScriptContext, ClientConnect)
### clientconnect(ScriptContext, ClientConnect)
Called when a client initiates a connection to the proxy. Note that
a connection can correspond to multiple HTTP requests.
###request(ScriptContext, Flow)
### request(ScriptContext, Flow)
Called when a client request has been received. The __Flow__ object is
guaranteed to have a non-None __request__ attribute.

BIN
doc-src/transparent.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 68 KiB

View File

@ -3,5 +3,4 @@ from countershape import Page
pages = [
Page("linux.html", "Linux"),
Page("osx.html", "OSX"),
Page("openbsd.html", "OpenBSD"),
]

Binary file not shown.

After

Width:  |  Height:  |  Size: 78 KiB

View File

@ -1,15 +0,0 @@
- command-line: _--upstream-cert_
- mitmproxy shortcut: _o_, then _u_
Normally, mitmproxy uses the target domain specified in a client's proxy
request to generate an interception certificate. When __upstream-cert__ mode is
activated a different procedure is followed: a connection is made to the
specified remote server to retrieve its __Common Name__ and __Subject
Alternative Names__. This feature is especially useful when the client
specifies an IP address rather than a host name in the proxy request. If this
is the case, we can only generate a certificate if we can establish the __CN__
and __SANs__ from the upstream server.
Note that __upstream-cert__ mode does not work when the remote server relies on
[Server Name Indication](http://en.wikipedia.org/wiki/Server_Name_Indication).
Luckily, SNI is still not very widely used.

50
examples/iframe_injector Executable file
View File

@ -0,0 +1,50 @@
#!/usr/bin/env python
"""
Zap encoding in requests and inject iframe after body tag in html responses.
Usage:
iframe_injector http://someurl/somefile.html
"""
from libmproxy import controller, proxy
import os
import sys
class InjectingMaster(controller.Master):
def __init__(self, server, iframe_url):
controller.Master.__init__(self, server)
self._iframe_url = iframe_url
def run(self):
try:
return controller.Master.run(self)
except KeyboardInterrupt:
self.shutdown()
def handle_request(self, msg):
if 'Accept-Encoding' in msg.headers:
msg.headers["Accept-Encoding"] = 'none'
msg._ack()
def handle_response(self, msg):
if msg.content:
c = msg.replace('<body>', '<body><iframe src="%s" frameborder="0" height="0" width="0"></iframe>' % self._iframe_url)
if c > 0:
print 'Iframe injected!'
msg._ack()
def main(argv):
if len(argv) != 2:
print "Usage: %s IFRAME_URL" % argv[0]
sys.exit(1)
iframe_url = argv[1]
config = proxy.ProxyConfig(
cacert = os.path.expanduser("~/.mitmproxy/mitmproxy-ca.pem")
)
server = proxy.ProxyServer(config, 8080)
print 'Starting proxy...'
m = InjectingMaster(server, iframe_url)
m.run()
if __name__ == '__main__':
main(sys.argv)

View File

@ -2,35 +2,49 @@ import binascii
import contrib.md5crypt as md5crypt
class NullProxyAuth():
""" No proxy auth at all (returns empty challange headers) """
def __init__(self, password_manager=None):
"""
No proxy auth at all (returns empty challange headers)
"""
def __init__(self, password_manager):
self.password_manager = password_manager
self.username = ""
def authenticate(self, auth_value):
""" Tests that the specified user is allowed to use the proxy (stub) """
def clean(self, headers):
"""
Clean up authentication headers, so they're not passed upstream.
"""
pass
def authenticate(self, headers):
"""
Tests that the user is allowed to use the proxy
"""
return True
def auth_challenge_headers(self):
""" Returns a dictionary containing the headers require to challenge the user """
"""
Returns a dictionary containing the headers require to challenge the user
"""
return {}
def get_username(self):
return self.username
class BasicProxyAuth(NullProxyAuth):
def __init__(self, password_manager, realm="mitmproxy"):
CHALLENGE_HEADER = 'Proxy-Authenticate'
AUTH_HEADER = 'Proxy-Authorization'
def __init__(self, password_manager, realm):
NullProxyAuth.__init__(self, password_manager)
self.realm = "mitmproxy"
self.realm = realm
def authenticate(self, auth_value):
if (not auth_value) or (not auth_value[0]):
return False;
def clean(self, headers):
del headers[self.AUTH_HEADER]
def authenticate(self, headers):
auth_value = headers.get(self.AUTH_HEADER, [])
if not auth_value:
return False
try:
scheme, username, password = self.parse_authorization_header(auth_value[0])
except:
scheme, username, password = self.parse_auth_value(auth_value[0])
except ValueError:
return False
if scheme.lower()!='basic':
return False
@ -40,14 +54,26 @@ class BasicProxyAuth(NullProxyAuth):
return True
def auth_challenge_headers(self):
return {'Proxy-Authenticate':'Basic realm="%s"'%self.realm}
return {self.CHALLENGE_HEADER:'Basic realm="%s"'%self.realm}
def parse_authorization_header(self, auth_value):
def unparse_auth_value(self, scheme, username, password):
v = binascii.b2a_base64(username + ":" + password)
return scheme + " " + v
def parse_auth_value(self, auth_value):
words = auth_value.split()
if len(words) != 2:
raise ValueError("Invalid basic auth credential.")
scheme = words[0]
user = binascii.a2b_base64(words[1])
username, password = user.split(':')
return scheme, username, password
try:
user = binascii.a2b_base64(words[1])
except binascii.Error:
raise ValueError("Invalid basic auth credential: user:password pair not valid base64: %s"%words[1])
parts = user.split(':')
if len(parts) != 2:
raise ValueError("Invalid basic auth credential: decoded user:password pair not valid: %s"%user)
return scheme, parts[0], parts[1]
class PasswordManager():
def __init__(self):
@ -56,8 +82,8 @@ class PasswordManager():
def test(self, username, password_token):
return False
class PermissivePasswordManager(PasswordManager):
class PermissivePasswordManager(PasswordManager):
def __init__(self):
PasswordManager.__init__(self)
@ -66,16 +92,17 @@ class PermissivePasswordManager(PasswordManager):
return True
return False
class HtpasswdPasswordManager(PasswordManager):
""" Read usernames and passwords from a file created by Apache htpasswd"""
class HtpasswdPasswordManager(PasswordManager):
"""
Read usernames and passwords from a file created by Apache htpasswd
"""
def __init__(self, filehandle):
PasswordManager.__init__(self)
entries = (line.strip().split(':') for line in filehandle)
valid_entries = (entry for entry in entries if len(entry)==2)
self.usernames = {username:token for username,token in valid_entries}
def test(self, username, password_token):
if username not in self.usernames:
return False
@ -84,8 +111,8 @@ class HtpasswdPasswordManager(PasswordManager):
expected = md5crypt.md5crypt(password_token, salt, '$'+magic+'$')
return expected==full_token
class SingleUserPasswordManager(PasswordManager):
class SingleUserPasswordManager(PasswordManager):
def __init__(self, username, password):
PasswordManager.__init__(self)
self.username = username

View File

@ -248,11 +248,6 @@ def common_options(parser):
help="Byte size limit of HTTP request and response bodies."\
" Understands k/m/g suffixes, i.e. 3m for 3 megabytes."
)
parser.add_argument(
"--cert-wait-time", type=float,
action="store", dest="cert_wait_time", default=0,
help="Wait for specified number of seconds after a new cert is generated. This can smooth over small discrepancies between the client and server times."
)
parser.add_argument(
"--no-upstream-cert", default=False,
@ -338,46 +333,29 @@ def common_options(parser):
group = parser.add_argument_group(
"Proxy Authentication",
"""
Specification of which users are allowed to access the proxy and the method used for authenticating them.
If authscheme is specified, one must specify a list of authorized users and their passwords.
In case that authscheme is not specified, or set to None, any list of authorized users will be ignored.
""".strip()
Specify which users are allowed to access the proxy and the method
used for authenticating them. These options are ignored if the
proxy is in transparent or reverse proxy mode.
"""
)
group.add_argument(
"--authscheme", type=str,
action="store", dest="authscheme", default=None, choices=["none", "basic"],
help="""
Specify the scheme used by the proxy to identify users.
If not none, requires the specification of a list of authorized users.
This option is ignored if the proxy is in transparent or reverse mode.
""".strip()
)
user_specification_group = group.add_mutually_exclusive_group()
user_specification_group.add_argument(
"--nonanonymous",
action="store_true", dest="auth_nonanonymous",
help="Allow access to any user as long as a username is specified. Ignores the provided password."
help="Allow access to any user long as a credentials are specified."
)
user_specification_group.add_argument(
"--singleuser",
action="store", dest="auth_singleuser", type=str,
help="Allows access to a single user as specified by the option value. Specify a username and password in the form username:password."
metavar="USER",
help="Allows access to a a single user, specified in the form username:password."
)
user_specification_group.add_argument(
"--htpasswd",
action="store", dest="auth_htpasswd", type=argparse.FileType('r'),
metavar="PATH",
help="Allow access to users specified in an Apache htpasswd file."
)
proxy.certificate_option_group(parser)

View File

@ -1387,6 +1387,8 @@ class FlowMaster(controller.Master):
self.kill_nonreplay = kill
def stop_server_playback(self):
if self.server_playback.exit:
self.shutdown()
self.server_playback = None
def do_server_playback(self, flow):
@ -1420,10 +1422,6 @@ class FlowMaster(controller.Master):
self.shutdown()
self.client_playback.tick(self)
if self.server_playback:
if self.server_playback.exit and self.server_playback.count() == 0:
self.shutdown()
return controller.Master.tick(self, q)
def duplicate_flow(self, f):

View File

@ -1,103 +1,23 @@
import socket, ctypes
# Python socket module does not have this constant
DIOCNATLOOK = 23
PFDEV = "/dev/pf"
class PF_STATE_XPORT(ctypes.Union):
"""
union pf_state_xport {
u_int16_t port;
u_int16_t call_id;
u_int32_t spi;
};
"""
_fields_ = [
("port", ctypes.c_uint),
("call_id", ctypes.c_uint),
("spi", ctypes.c_ulong),
]
class PF_ADDR(ctypes.Union):
"""
struct pf_addr {
union {
struct in_addr v4;
struct in6_addr v6;
u_int8_t addr8[16];
u_int16_t addr16[8];
u_int32_t addr32[4];
} pfa;
}
"""
_fields_ = [
("addr8", ctypes.c_byte * 2),
("addr16", ctypes.c_byte * 4),
("addr32", ctypes.c_byte * 8),
]
class PFIOC_NATLOOK(ctypes.Structure):
"""
struct pfioc_natlook {
struct pf_addr saddr;
struct pf_addr daddr;
struct pf_addr rsaddr;
struct pf_addr rdaddr;
#ifndef NO_APPLE_EXTENSIONS
union pf_state_xport sxport;
union pf_state_xport dxport;
union pf_state_xport rsxport;
union pf_state_xport rdxport;
sa_family_t af;
u_int8_t proto;
u_int8_t proto_variant;
u_int8_t direction;
#else
u_int16_t sport;
u_int16_t dport;
u_int16_t rsport;
u_int16_t rdport;
sa_family_t af;
u_int8_t proto;
u_int8_t direction;
#endif
};
"""
_fields_ = [
("saddr", PF_ADDR),
("daddr", PF_ADDR),
("rsaddr", PF_ADDR),
("rdaddr", PF_ADDR),
("sxport", PF_STATE_XPORT),
("dxport", PF_STATE_XPORT),
("rsxport", PF_STATE_XPORT),
("rdxport", PF_STATE_XPORT),
("af", ctypes.c_uint),
("proto", ctypes.c_ushort),
("proto_variant", ctypes.c_ushort),
("direction", ctypes.c_ushort),
]
import subprocess
import pf
"""
Doing this the "right" way by using DIOCNATLOOK on the pf device turns out
to be a pain. Apple has made a number of modifications to the data
structures returned, and compiling userspace tools to test and work with
this turns out to be a pain in the ass. Parsing pfctl output is short,
simple, and works.
"""
class Resolver:
STATECMD = ("sudo", "-n", "/sbin/pfctl", "-s", "state")
def __init__(self):
self.pfdev = open(PFDEV, "r")
pass
def original_addr(self, csock):
"""
The following sttruct defintions are plucked from the current XNU source, found here:
http://www.opensource.apple.com/source/xnu/xnu-1699.26.8/bsd/net/pfvar.h
union pf_state_xport {
u_int16_t port;
u_int16_t call_id;
u_int32_t spi;
};
"""
pass
peer = csock.getpeername()
try:
stxt = subprocess.check_output(self.STATECMD, stderr=subprocess.STDOUT)
except subprocess.CalledProcessError:
return None
return pf.lookup(peer[0], peer[1], stxt)

16
libmproxy/platform/pf.py Normal file
View File

@ -0,0 +1,16 @@
def lookup(address, port, s):
"""
Parse the pfctl state output s, to look up the destination host
matching the client (address, port).
Returns an (address, port) tuple, or None.
"""
spec = "%s:%s"%(address, port)
for i in s.split("\n"):
if "ESTABLISHED:ESTABLISHED" in i and spec in i:
s = i.split()
if len(s) > 4:
s = s[4].split(":")
if len(s) == 2:
return s[0], int(s[1])

View File

@ -38,19 +38,19 @@ class Log(controller.Msg):
class ProxyConfig:
def __init__(self, certfile = None, cacert = None, clientcerts = None, cert_wait_time=0, no_upstream_cert=False, body_size_limit = None, reverse_proxy=None, transparent_proxy=None, certdir = None, authenticator=None):
def __init__(self, certfile = None, cacert = None, clientcerts = None, no_upstream_cert=False, body_size_limit = None, reverse_proxy=None, transparent_proxy=None, certdir = None, authenticator=None):
assert not (reverse_proxy and transparent_proxy)
self.certfile = certfile
self.cacert = cacert
self.clientcerts = clientcerts
self.certdir = certdir
self.cert_wait_time = cert_wait_time
self.no_upstream_cert = no_upstream_cert
self.body_size_limit = body_size_limit
self.reverse_proxy = reverse_proxy
self.transparent_proxy = transparent_proxy
self.authenticator = authenticator
self.certstore = certutils.CertStore(certdir)
class RequestReplayThread(threading.Thread):
def __init__(self, config, flow, masterq):
self.config, self.flow, self.masterq = config, flow, masterq
@ -247,8 +247,7 @@ class ProxyHandler(tcp.BaseHandler):
raise ProxyError(502, "Unable to get remote cert: %s"%str(v))
sans = cert.altnames
host = cert.cn.decode("utf8").encode("idna")
ret = certutils.dummy_cert(self.config.certdir, self.config.cacert, host, sans)
time.sleep(self.config.cert_wait_time)
ret = self.config.certstore.get_cert(host, sans, self.config.cacert)
if not ret:
raise ProxyError(502, "mitmproxy: Unable to generate dummy cert.")
return ret
@ -270,7 +269,10 @@ class ProxyHandler(tcp.BaseHandler):
def read_request(self, client_conn):
self.rfile.reset_timestamps()
if self.config.transparent_proxy:
host, port = self.config.transparent_proxy["resolver"].original_addr(self.connection)
orig = self.config.transparent_proxy["resolver"].original_addr(self.connection)
if not orig:
raise ProxyError(502, "Transparent mode failure: could not resolve original destination.")
host, port = orig
if not self.ssl_established and (port in self.config.transparent_proxy["sslports"]):
scheme = "https"
certfile = self.find_cert(host, port, None)
@ -311,7 +313,7 @@ class ProxyHandler(tcp.BaseHandler):
line = self.get_line(self.rfile)
if line == "":
return None
if line.startswith("CONNECT"):
if http.parse_init_connect(line):
r = http.parse_init_connect(line)
if not r:
raise ProxyError(400, "Bad HTTP request line: %s"%repr(line))
@ -332,14 +334,15 @@ class ProxyHandler(tcp.BaseHandler):
raise ProxyError(400, str(v))
self.proxy_connect_state = (host, port, httpversion)
line = self.rfile.readline(line)
if self.proxy_connect_state:
host, port, httpversion = self.proxy_connect_state
r = http.parse_init_http(line)
if not r:
raise ProxyError(400, "Bad HTTP request line: %s"%repr(line))
method, path, httpversion = r
headers = self.read_headers(authenticate=False)
host, port, _ = self.proxy_connect_state
content = http.read_http_body_request(
self.rfile, self.wfile, headers, httpversion, self.config.body_size_limit
)
@ -348,7 +351,7 @@ class ProxyHandler(tcp.BaseHandler):
r = http.parse_init_proxy(line)
if not r:
raise ProxyError(400, "Bad HTTP request line: %s"%repr(line))
method, scheme, host, port, path, httpversion = http.parse_init_proxy(line)
method, scheme, host, port, path, httpversion = r
headers = self.read_headers(authenticate=True)
content = http.read_http_body_request(
self.rfile, self.wfile, headers, httpversion, self.config.body_size_limit
@ -359,8 +362,15 @@ class ProxyHandler(tcp.BaseHandler):
headers = http.read_headers(self.rfile)
if headers is None:
raise ProxyError(400, "Invalid headers")
if authenticate and self.config.authenticator and not self.config.authenticator.authenticate(headers.get('Proxy-Authorization', [])):
raise ProxyError(407, "Proxy Authentication Required", self.config.authenticator.auth_challenge_headers())
if authenticate and self.config.authenticator:
if self.config.authenticator.authenticate(headers):
self.config.authenticator.clean(headers)
else:
raise ProxyError(
407,
"Proxy Authentication Required",
self.config.authenticator.auth_challenge_headers()
)
return headers
def send_response(self, response):
@ -405,13 +415,6 @@ class ProxyServer(tcp.TCPServer):
except socket.error, v:
raise ProxyServerError('Error starting proxy server: ' + v.strerror)
self.masterq = None
if config.certdir:
self.certdir = config.certdir
self.remove_certdir = False
else:
self.certdir = tempfile.mkdtemp(prefix="mitmproxy")
config.certdir = self.certdir
self.remove_certdir = True
self.apps = AppRegistry()
def start_slave(self, klass, masterq):
@ -430,11 +433,7 @@ class ProxyServer(tcp.TCPServer):
pass
def handle_shutdown(self):
try:
if self.remove_certdir:
shutil.rmtree(self.certdir)
except OSError:
pass
self.config.certstore.cleanup()
class AppRegistry:
@ -537,30 +536,24 @@ def process_proxy_options(parser, options):
if not os.path.exists(options.certdir) or not os.path.isdir(options.certdir):
parser.error("Dummy cert directory does not exist or is not a directory: %s"%options.certdir)
if options.authscheme and (options.authscheme!='none'):
if not (options.auth_nonanonymous or options.auth_singleuser or options.auth_htpasswd):
parser.error("Proxy authentication scheme is specified, but no allowed user list is given.")
if options.auth_singleuser and len(options.auth_singleuser.split(':'))!=2:
parser.error("Authorized user is not given in correct format username:password")
if options.auth_nonanonymous:
password_manager = authentication.PermissivePasswordManager()
elif options.auth_singleuser:
if (options.auth_nonanonymous or options.auth_singleuser or options.auth_htpasswd):
if options.auth_singleuser:
if len(options.auth_singleuser.split(':')) != 2:
parser.error("Please specify user in the format username:password")
username, password = options.auth_singleuser.split(':')
password_manager = authentication.SingleUserPasswordManager(username, password)
elif options.auth_nonanonymous:
password_manager = authentication.PermissivePasswordManager()
elif options.auth_htpasswd:
password_manager = authentication.HtpasswdPasswordManager(options.auth_htpasswd)
# in the meanwhile, basic auth is the only true authentication scheme we support
# so just use it
authenticator = authentication.BasicProxyAuth(password_manager)
authenticator = authentication.BasicProxyAuth(password_manager, "mitmproxy")
else:
authenticator = authentication.NullProxyAuth(None)
return ProxyConfig(
certfile = options.cert,
cacert = cacert,
clientcerts = options.clientcerts,
cert_wait_time = options.cert_wait_time,
body_size_limit = body_size_limit,
no_upstream_cert = options.no_upstream_cert,
reverse_proxy = rp,

View File

@ -93,7 +93,4 @@ setup(
"Topic :: Software Development :: Testing"
],
install_requires=["netlib", "urwid>=1.1", "pyasn1>0.1.2", "pyopenssl>=0.12", "PIL", "lxml"],
dependency_links=[
'https://github.com/cortesi/netlib/tarball/master#egg=netlib-0.1'
],
)

4
test/data/pf01 Normal file
View File

@ -0,0 +1,4 @@
No ALTQ support in kernel
ALTQ related functions disabled
ALL tcp 127.0.0.1:8080 <- 5.5.5.6:80 <- 192.168.1.111:40001 FIN_WAIT_2:FIN_WAIT_2
ALL tcp 127.0.0.1:8080 <- 5.5.5.5:80 <- 192.168.1.111:40000 ESTABLISHED:ESTABLISHED

View File

@ -0,0 +1,58 @@
import binascii
from libmproxy import authentication
from netlib import odict
import tutils
class TestNullProxyAuth:
def test_simple(self):
na = authentication.NullProxyAuth(authentication.PermissivePasswordManager())
assert not na.auth_challenge_headers()
assert na.authenticate("foo")
na.clean({})
class TestBasicProxyAuth:
def test_simple(self):
ba = authentication.BasicProxyAuth(authentication.PermissivePasswordManager(), "test")
h = odict.ODictCaseless()
assert ba.auth_challenge_headers()
assert not ba.authenticate(h)
def test_parse_auth_value(self):
ba = authentication.BasicProxyAuth(authentication.PermissivePasswordManager(), "test")
vals = ("basic", "foo", "bar")
assert ba.parse_auth_value(ba.unparse_auth_value(*vals)) == vals
tutils.raises(ValueError, ba.parse_auth_value, "")
tutils.raises(ValueError, ba.parse_auth_value, "foo bar")
v = "basic " + binascii.b2a_base64("foo")
tutils.raises(ValueError, ba.parse_auth_value, v)
def test_authenticate_clean(self):
ba = authentication.BasicProxyAuth(authentication.PermissivePasswordManager(), "test")
hdrs = odict.ODictCaseless()
vals = ("basic", "foo", "bar")
hdrs[ba.AUTH_HEADER] = [ba.unparse_auth_value(*vals)]
assert ba.authenticate(hdrs)
ba.clean(hdrs)
assert not ba.AUTH_HEADER in hdrs
hdrs[ba.AUTH_HEADER] = [""]
assert not ba.authenticate(hdrs)
hdrs[ba.AUTH_HEADER] = ["foo"]
assert not ba.authenticate(hdrs)
vals = ("foo", "foo", "bar")
hdrs[ba.AUTH_HEADER] = [ba.unparse_auth_value(*vals)]
assert not ba.authenticate(hdrs)
ba = authentication.BasicProxyAuth(authentication.PasswordManager(), "test")
vals = ("basic", "foo", "bar")
hdrs[ba.AUTH_HEADER] = [ba.unparse_auth_value(*vals)]
assert not ba.authenticate(hdrs)

View File

@ -48,6 +48,15 @@ class TestDumpMaster:
fw.add(t)
f.close()
def test_error(self):
cs = StringIO()
o = dump.Options(verbosity=1)
m = dump.DumpMaster(None, o, None, outfile=cs)
f = tutils.tflow_err()
m.handle_request(f.request)
assert m.handle_error(f.error)
assert "error" in cs.getvalue()
def test_replay(self):
cs = StringIO()

View File

@ -624,6 +624,7 @@ class TestFlowMaster:
fm.handle_error(flow.Error(f.request, "error"))
def test_server_playback(self):
controller.should_exit = False
s = flow.State()
f = tutils.tflow()
@ -641,8 +642,9 @@ class TestFlowMaster:
r = tutils.tflow()
r.request.content = "gibble"
assert not fm.do_server_playback(r)
assert fm.do_server_playback(tutils.tflow())
fm.start_server_playback(pb, False, [], True, False)
q = Queue.Queue()
fm.tick(q)
assert controller.should_exit
@ -650,6 +652,20 @@ class TestFlowMaster:
fm.stop_server_playback()
assert not fm.server_playback
def test_server_playback_kill(self):
s = flow.State()
f = tutils.tflow()
f.response = tutils.tresp(f.request)
pb = [f]
fm = flow.FlowMaster(None, s)
fm.refresh_server_playback = True
fm.start_server_playback(pb, True, [], False, False)
f = tutils.tflow()
f.request.host = "nonexistent"
fm.process_new_request(f)
assert "killed" in f.error.msg
def test_stickycookie(self):
s = flow.State()
fm = flow.FlowMaster(None, s)

13
test/test_platform_pf.py Normal file
View File

@ -0,0 +1,13 @@
import tutils
from libmproxy.platform import pf
class TestLookup:
def test_simple(self):
p = tutils.test_data.path("data/pf01")
d = open(p).read()
assert pf.lookup("192.168.1.111", 40000, d) == ("5.5.5.5", 80)
assert not pf.lookup("192.168.1.112", 40000, d)
assert not pf.lookup("192.168.1.111", 40001, d)

View File

@ -5,5 +5,3 @@ import socket, tempfile, ssl, subprocess
addr = socket.gethostbyname(sys.argv[1])
print ssl.get_server_certificate((addr, 443))

View File

@ -1,17 +0,0 @@
#!/usr/bin/env python
import sys
sys.path.insert(0, "../../")
from libmproxy import certutils
if len(sys.argv) > 2:
port = int(sys.argv[2])
else:
pport = 443
cn, san = certutils.get_remote_cn(sys.argv[1], port)
print cn
if san:
for i in san:
print "\t", i

View File

@ -4,7 +4,7 @@ from contextlib import contextmanager
from libmproxy import proxy, flow, controller, utils
from netlib import certutils
import human_curl as hurl
import libpathod.test
import libpathod.test, libpathod.pathoc
def treq(conn=None):
if not conn:
@ -194,7 +194,6 @@ class ReverseProxTest(ProxTestBase):
return r
@contextmanager
def tmpdir(*args, **kwargs):
orig_workdir = os.getcwd()
@ -245,4 +244,5 @@ def raises(exc, obj, *args, **kwargs):
)
raise AssertionError("No exception raised.")
test_data = utils.Data(__name__)