Apache2 - Bw Mod v0.6 Stable 

Author       : Ivan Barrera A. (Bruce)

HomePage     : Http://Ivn.cl/apache

Release Date : 28-02-2005

Status       : Functional. Tested under medium and heavy load.
                 
License      : Ivn Project License. [bw_mod-license.txt]
               It must be included in every package containing this file.
               If it doesn't, please delete this software.
               You can get a copy in Http://Ivn.cl
               As Ivn Project License isnt yet an OSI approved license,
               You can use and include the Apache 2.0 License.
  
Platform     : Linux/x86         (Tested with Fedora Core 3, Suse, etc)
               FreeBSD/x86 v5.2  (Others versions might work as well) 
               MacOS X/Ppc x86   (Darwin on x86 platform)
               Solaris 8/sparc   (Some notes on compile.)
               Microsoft Windows (Win XP, Win2003. Others should work)

Notes        : This is a stable version of bw_mod. It works fine with
               almost any MPM (tested with WinNT/prefork/Worker MPM).
               It has almost every known bug fixed. If any bug appear,
               it will be fixed at the next stable release.
               From now on, every bugfix, feature request, comment, 
               must be addressed at the webpage.

Known Bugs   : None in this version.
               However, there is a limitation of this module due to a 
               lack of documentation on the Apach2 API.
               As the mod isn't able to detect the real bandwidth a client
               is using, it keeps sending data, at the determined rate 
               (the bw limit you imposed). If the client is downloading to
               a lower rate (connection limitation) the mod keeps the rate
               imposed, until finished. But the client will keep the 
               connection open as long as it takes to finish the download.
               This have a negative impact on the mod, not being able to 
               know exactly how many *real* clients there are, and the real
               bandwidth used, so the remaining bw be divided on the others
               clients.
               If anyone knows how to get the bandwidth used by a client in
               realtime, please, contact me. 



 If you want to support the development of this, and other software, you can
    contribute with the author, either with Money or Hardware donations.

     If you are making profit from this product, you are encouraged to
        get a paid license, or make a contribution with the Author

          To make a donation, contact the Author at Bruce@Ivn.cl

------------------------------------------------------------------------------

Contents :

1 .- Notices
 1.1 - ChangeLog
 1.2 - ToDo

2 .- Installing
 2.1 - Windows
 2.2 - Linux

3 .- Getting it to Work, Directives
 3.1 - BandWidthModule
 3.2 - BandWidthDebug
 3.3 - ForceBandWidthModule
 3.4 - BandWidth
 3.5 - MinBandWidth
 3.6 - LargeFileLimit
 3.7 - BandWidthPacket
 3.8 - BandWidthError
 3.9 - MaxConnection 

4 .- FAQ

5 .- Third Party Modifications

6 .- Thanks to ... [ Not finished yet ]
    
------------------------------------------------------------------------------

1.- Notices

 1.1 - ChangeLog :

 v0.6 Stable (28-02-2005)
  - Ok.. I made some mistakes the last "stable" release. I think the stress
   of knowing that i'll have to start working hard, made me collpase.
    Some FreeBSD (and other) guys, were having segfaults. This primarily 
   cause i changed the filter type from TRANSCODE to NETWORK. I still dont
   know why. Probably i was thinking on a next release when working on that.
  - Changed the r->finfo.size to bblen again. Mistakes... mistakes...
  - I changed 0.5 -> 0.6 cause i've released too much fixes to 0.5. Time to 
   move forward on revision numbers.

 v0.5 Stable (20-02-2005)
  - Tested with Worker MPM, and WinNT MPM
  - Fixed a bug that caused bw_mod don't work if EnableMMAP was disabled.
  - If there is a total reply size availbale, match that instead of file 
   eize. This is useful when limiting scripts that ouput files and stuff.
  - Added Windows Support. bw_mod v0.5 WR availbale to download (binary)
  - Some minor bugs fixed.
  - The excess function was not working. It is disabled until i discover how
   to determine the real bandwidth a client is using.
  - Added BandWidthError directive. Allows to deliver personalized error 
   when reaching maxconnections.
  - First release of the Ivn Project License. Until it is OSI approved, you
   can use the Apache 2.0 License.

 v0.5rc1 (21-01-2005)
  - I'm doing this release as a candidate release, cause i need some testing
   besides myself. If it works flawlessly, i'm moving to v0.5.
  - New bucket-split algorithm. 
  - More configuration changes. Now MaxConnection can be by clients. And File 
   Size limit, can be by extensions.
  - Some error checking added, some debug info added (commented till next
   release)
  - New netmask format support. Thanks goes to Ale Feltes Quenhan 
    <ale@roshka.com.py> who provided a nice patch for v0.1.
  - Added support to compile under FreeBSD 5.2. Need more testing.
  - Added support to compile under MaxOS X. Need more testing.
  - Changed internal name to bw_module... so apxs doesnt complain about.
   ( i hate that... the name is bw_mod :'(  )

 v0.4 (not released)
  - Almost total rewrite of the mod. Some helper functions keep the same.
  - The mod doesn't use the byterange hack i did before. Now it works as
   an Output Filter, as it should have been in the beggining.
  - Counting, and stats, are done in shared memory now. The system allocate
   enough memory to hold every configuration. Some directives changed.
  - htaccess is removed from suppor for now. It causes some weird thing with
   my shared memory implementation.
  - Partial download, file symlinks, are not a problem anymore, as we dont
   use it. The filter takes care of all this.

 v0.3
  - Mayor rewrite on counting routines. Using shared memory to count.

 v0.2 (not released)
  - Fixed partial download problem
  - Added some error checking routines
  

 v0.1 (2004.10.29)
  - Ported from mod_bandwidth written by Yann Stettler for Apache 1.3

------------------------------------------------------------------------------

 1.2 - ToDo :

 - Count Connections using scoreboard. Although it might add too much overhead
 - Learn how to get the bw used in realtime. Once learnt, i can fix the
  connection counting problem, and the excess bw function.
 - BandWidth/Connection limit based on Agent
 - BandWidth Available to Lists of hosts (via file or comma separated list)
 - MaxConnections Per Each IP
 - Handler to see current status
 - htaccess support.
 - Add functions to throttle connections like mod_bwshare o mod_throttle
 - File Size Limit based on Mime Type (? I'm not sure this is a good idea.
                                        If noone ask for it, i'm going to dish
                                        this idea )

 In the 1.0 revision, the mod will have :

 - More advanced way to use settings. (config files for the mod, etc).
 - Web configurable.

 - Please, post any features request, bugs, ideas, to the Homepage.

------------------------------------------------------------------------------

2.- How To Install :

 2.1 - Windows

   In Windows, you have to download the binary dll from the site (or compile
  one yourself) that matches your apache version, and Install it under modules
  on your apache tree. Then edit httpd.conf, and add the LoadModule sentence.
  If there is no matching binary dll with your version of apache (the latest)
  you can ask me to compile it for you. Post a message in the home site as a
  feature request.

  Example :

    Download bw_mod-2.0.53.dll from the home site, to c:\apache2\modules
    Edit httpd.conf, and add LoadModule bw_module modules/bw_mod-2.0.53.dll
    Restart Apache.

  Note : The sources to windows, are the same. I didnt include the MSVC 6
        project files, cause i dont have a license to use it. anyways, you
        should be able to figure out, how to compile, following apache standar
        modules.

 2.2 - Linux

   Well.. (under *nix) you *have* to compile it..
  It might sound scary, but it's easy. There is an easy way, and the hard way.
  If the easy way doesn't work for you, use the hard way.

  REQUIREMENTS :

   You will need apache2 headers in the include path. In redhat/suse or others
  this mean apache-devel or httpd-devel installed.
   You also need support for SHM in your OS. Usually you will have this.

 - Easy Way :

   For this to work, you MUST have apxs (or apxs2) installed. You might need
  to use it full path (i.e. /usr/sbin/apxs .....). Well, you have to do this :

   apxs -i -a -c bw_mod-0.6.c
   or
   apxs2 -i -a -c bw_mod-0.6.c

   This will bring out some stuff... nothing to worry (unless you see error)
  If it says ok, then you are ready. Restart apache (service apache restart on
  redhat, mandrake, and others... apachectl restart .. rcapache2 restart or... 
  well, you should know)

  Note On Solaris Users :

   If you got problems compiling it on Solaris, remember to check you have 
  libgcc correctly installed, and the ld_library_path set up correctly. 
   I didnt, so i compiled this way :

   export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:/usr/local/lib
   apxs -i -a -c bw_mod-0.6.c -L/usr/local/lib -lgcc_s
               
   And then started apache, and everything worked fine.

  Note On SuSe Users :

   You NEED to have installed apache2 header files (apache2-devel rpm).
  Otherwise you'll get lots of include files error.
   Other thing i noticed, is that apxs (you have to use apxs2) didnt put the
  config in the file i needed, and the init scripts overwrite the
  loadmodule.conf file everytime you start apache, so you have to add the
  LoadModule bw_mod.... sentence, in httpd.conf (/etc/apache2/httpd.conf)
   Something Like : (First 2 lines, are default in the file)

    # generated from APACHE_MODULES in /etc/sysconfig/apache2
    Include /etc/apache2/sysconfig.d/loadmodule.conf
    LoadModule bw_module /usr/lib/apache2/bw_mod-0.6.so

 - Hard Way

   If usgint the easy way, you turned to have some .o files.. you are almost
  done... skip to the part of installing the module.
   Back to the hard way..... you might notice that you dont have apxs,
  dont know why (maybe the dog ate it). Well. try the following (and please
  do it on a newly-fresh created directory for this purpose) :
  (this does not necessarily work on all cases)

    libtool --silent --mode=compile gcc  -g -O2 -pthread    -DLINUX=2 \
        -D_REENTRANT -D_XOPEN_SOURCE=500 -D_BSD_SOURCE -D_SVID_SOURCE \
        -I/usr/include/httpd \
        -I/usr/include/apr-0 -Wall -g\
        -prefer-pic -c bw_mod-0.6.c && touch bw_mod-0.6.slo


    libtool --silent --mode=link gcc  -g -O2 -pthread    -DLINUX=2 \
        -D_REENTRANT -D_XOPEN_SOURCE=500 -D_BSD_SOURCE -D_SVID_SOURCE \
        -D_GNU_SOURCE -DAP_HAVE_DESIGNATED_INITIALIZER \
        -I/usr/include/httpd \
        -I/usr/include/apr-0 -Wall -g\
        -export-dynamic -o bw_mod-0.6.la  -rpath /usr/lib/httpd/modules \
        -module -avoid-version  bw_mod-0.6.lo

    (this cleans some unneeded files)
    rm -rf *.a *.la *.lo *.slo *.o *.loT
    mv .libs/*.so .
    rm -rf .libs

    Note that you need to know where are your httpd and apr includes.
    (dont ask me where they are.. you are supossed to know)
    If this worked... we are good to install the module.

   * Installing the module (hey.. this is part of the hard way)

    Ok, either if the easy way didnt install the mod, or if you did the
   hard way, now you must install the module by hand.
    Is easy as copying the file (usually bw_mod-0.6.so) to the apache
   modules directory (usually /etc/httpd/modules or 
   /usr/local/libexec/apache2/) and then adding the following line at
   httpd.conf (better of if you add it at the last part of all LoadModule
   sentences) :

    LoadModule bw_module bw_mod-0.6.so

    Please, take a look at the other LoadModule sentences. You may need
   to add a path before the .so file. 
   (i.e LoadModule bw_module libexec/apache2/bw_mod-0.6.so)



  If you didn't manage to get it installed, drop me a letter. But please
 be sure you tried everything. Sometimes the simplest way, is the better.
------------------------------------------------------------------------------

3.- Getting it to Work :


  Ok.. this is the most confusing part. (yeh, most of us think the installing
 part is the hardest xD )

  This mod, is able to limit bandwidth usage on every virtual host or
 directory. htaccess files are not supported yet, cause i've been having some
 serious segfaults when implementing it.

 * Configuration Directives
 *****************************************************************************

 3.1 - BandWidthModule [On|Off]

    You need to set this to On, for the mod to work.. By default, the mod is
   disabled, and wont limit anything.

   Example :
              BandWidthModule On

 3.2 - BandWidthDebug [On|Off]
 
    When enabled (disabled by default) the log will output lots of data to the
   error log. This data is for debugging purposes, and is usually not needed.
    If you are curious, you can enable. Please note, that this will make your
   logs grow a LOT.
   
   Example :
              BandWidthDebug On

 3.3 - ForceBandWidthModule [On|Off]
 
    By default, the mod will catch every request. This was done because it is
   easier to configure.
    If you disable it, you will have to add the output filter by hand. This is
   useful is you want only some request being processed by bw_mod.
   
   Example :
              ForceBandWidthModule Off
              AddOutputFilterByType BW_MOD text/html text/plain


 3.4 - BandWidth [From] [bytes/s]

    This takes 2 parameters. From is the origin of the connections. It could
   be a full host, part of a domain, an ip address, a network mask (i.e
   192.168.0.0/24 or 192.168.0.0/255.255.255.0) or all.
    The second parameter indicates the total speed available to the Origin.
    If speed is 0, there is no limit.

   Example :
            BandWidth localhost 10240
            BandWidth 192.168.218.5 0

            ( Order is relevant. First entries have precedence )

 3.5 - MinBandWidth [From] [bytes/s]

    This takes 2 parameters. From is the origin of the connections. It could
   be a full host, part of a domain, an ip address, a network mask (i.e
   192.168.0.0/24 or 192.168.0.0/255.255.255.0) or all.
    The second parameter indicates the minimun speed each client will have.
   What does this mean ? If you have a total of 100kbytes speed, and you put
   MinBandWidth at 50kbytes, it doesnt matter how many clients you have, all
   of them will have at minimun 50kbytes of total speed to download.
    If speed is 0, you will be using the default minimun (256 bytes/s).
    There is a special value of -1. This value means that each client, will
   have a top speed determined by the BandWidth directive. See the examples.

   Examples :
              BandWidth    all 102400
              MinBandWidth all 50000
 
             The example above, will have a top speed of 100kb for the 1º
            client. If more clients come, it will be splitted accordingly but
            everyone will have at least 50kb (even if you have 50 clients)

              BandWidth    all 50000
              MinBandWidth all -1

             This example, makes everyone have 50kb as top speed.

 3.6 - LargeFileLimit [Type] [Minimum Size] [bytes/s]

    Type, is the last part of a file, or * for all. You can use .tgz to match 
   only tar-compressed files, .avi to match video files, or * to match all.
    Minimum Size, is the size (in kbytes) of the file, to be matched. That way
   you can match huge video files that hog your bandwidth.
    The last parameter... is obvious. The speed allowed.

   Example :
             LargeFileLimit .avi 500 10240

             This limits .avi files over (or equal to) 500kb to 10kbytes/s

 3.7 - BandWidthPacket [Size]

    Probably you never need to touch this. It defaults to 8192 which is good
   for almost any speed.
    It must be a size between 1024 and 131072. A Small packet will cause the
   top speed to be lower, and the mod using more time splitting. If you use
   a Size too big, the mod will adjust it to lower speeds.

 3.8 - BandWidthError [Error]

    This directives is useful to deliver a personalized error code.
    At default, when maxconnections is reached, the mod will issue a 503 
   HTTP_SERVICE_UNAVAILABLE code. For some users, it is annoying to have an
   error message, and dont knowing why. You could use an ErrorDocument to 
   point error 503 to a page explaining that you are under a heavy load of
   connections, but sometimes 503 isn't issued by the mod.
    So, with this directive, you can set the error code to return when
   maxconnections is reached. You can use any error code between 300 and 599.
   Please note, that some of the error codes are already used, so before using
   any number, take a look to a list of the codes (search for http error codes
   in google). 
    When testing, i've used the error code 510, which hasn't been defined yet.

    And Example, with Personalized Error Page :

      ErrorDocument 510 /errors/maxconexceeded.html
      BandWidthError 510

    Note : Sometimes, the personalized page didn't appear. I'm not sure, but
          in many cases, it got fixed, by making the page size over 1024bytes.
           Anyways, if you need help using ErrorDocument, refer to the apache
          Documentation.
 
 3.9 - MaxConnection [From] [Max]

    This takes 2 parameters. From is the origin of the connections. It could
   be a full host, part of a domain, an ip address, a network mask (i.e
   192.168.0.0/24 or 192.168.0.0/255.255.255.0) or all.
    The second parameter, is the max connections allowed from the origin. Any
   connection over Max, will get a 503 Service Temporarily Unavailable

    There is a catch. You NEED to have a BandWidth limit for the same origin.
   It doesnt need to be a low limit. You can use an unlimited setting.
    You might wonder why. It's because im using them same memory space of the
   bandwidth limit, to count the connections, so i can save memory space.
    If you dont put a BandWidth using the same origin, MaxConnections will be
   ignored.

   Example :
              BandWidth all 0
              MaxConnection all 20
    or
              BandWidth all 0
              BandWidth 192.168.0.0/24 10240
              MaxConnection all 20
              MaxConnection 192.168.0.0/24 5


  Please, rememeber that every speed, will depend mostly on your connection.
 You cant get more speed if you dont have it.

  Remember also.. if you dont follow the instructions, and get some weird 
 results, recheck your config before sending me an email.

------------------------------------------------------------------------------

4.- FAQ

(No particular order)

1.- Why should i use bw_mod ?

    If you want to restrict the top speed a site is able to use, or limit the
  max connections allowed per site, or just to try the mod.
    Some people told me, they use it primarily to stop small sites hogging 
  all the bandwidth when serving video, images, or other content.

2.- How do i ... ?

    First, read the documentation. it is pretty straightforward to use.
  If you can't make it work, or if you want to ask for a feature, visit the
  home site, and post a request. Remember to read the documentation and the
  faq. If the request is already posted, i'll just delete the duplicates.

3.- What's the difference with mod_bwshare, mod_throttle, etc ?

    The main difference, is that this mod, is aimed to the Apache 2 API.
  Some other differences, is, how this mod works, and the directives it 
  implements.
    I took some ideas from other mods, as the shared memory implementation
  (mod_bandwidth2 from Tim Verhoeven). Most of the directives, are in origin
  from mod_bandiwdth for apache 1.

4.- How does it works ?

    The mod, will set a shared memory holding all of the configuration you
  make. In this space, it will also, keep a "count" of the info currently
  using (as current connections, bw used, time, and bytes sent).
    When you assign a bw limit, the mod will "split" the data, and will send
  it piece by piece, with a small delay between pieces. The delay will be
  adjusted so at least 1 piece is sent in a second, thus eviting browser
  timeout.
    If there are two or more clients downloading from the same vhost, the
  limit will be "splitted" too. So, if you have a bw limit of 16Kb and two
  clients, each one will have 8Kb to download. You can also set a fixed 
  download rate, so each client will have a fixed maximun download rate.
    This is a simple explanation of how this works. Take a look at the code
  if you want to know more about it.

5.- Can you make it do ... ? 

    Post a request for a feature in the home site. I'll respond there.

6.- Can you make bw_mod work for ... ?

    See question 5. Anyways, if i dont own (or have access) to the hardware
  needed, i won't be able to help you.

7.- I'm having some trouble in windows ... 

    I cannot support windows in an official way. I do not own a licensed copy
  of Windows, or Visual C.
    Anyways, post your problem in the home site. 

8.- The mod is not limiting certain Directory

    Ok... first, read the documentation. Then the FAQ. If it isn't working,
  then look if you have defined correctly the limits within that directory.
    If you have a limit in a vhost, and inside the vhost, a directory with
  another limit, a new context with the configs of the directory is created,
  and only have the configurations you added there. 

  In example :

  <VirtualHost *>
    BandWidthModule On
    BandWidth all 16384
    LargeFileLimit * 500 4096
    <Directory />
      LargeFileLimit * 100 1024
    </Directory>

  This wont limit Directory / to 16384. The Directory wont "inherit" the
 settings from the vhost if you use some of the mod's directives.


9.- Can i contribute to the development of other software from Ivn Project ?

  Yes, you can.
  Any contribution is welcome. Hardware, Money, hosting, etc.


10.- Why is your english "funny" ?

  Well.. as you may have noticed, i'm from Chile. My primary language is 
 Spanish. I'm usually chatting, and doing other stuff in english, but it isn't
 perfect. If you feel that i'm writing something in a bad or confusing way, 
 just let me know. If you have a correction to make to this doc, also, let me
 know. 

------------------------------------------------------------------------------

5 .- Third Party Modifications 

  If you did some modifications to the source code, and are redistributing it,
please add a comment for each modification you did. This will help others to
understand differences between the original module, and the modified version.

  You can modify this file to reflect all the new features you add (or erase),
but remember to keep the original credits, and add yours at the end. 

Modifications :

  - 
  - 

Links to the Patch Files :

  - 
  - 

------------------------------------------------------------------------------

          This software was developed by Ivn Systems/Software. 
         You can get the Original Source at Http://Ivn.cl/apache 
  

 Ivan Barrera A. 
 Ivn Systems Software                                      -(Bruce@Ivn.cl)-


