An Introduction to Apache 2.0 Page 3
The last big change to modules is how a module registers a function to be called for a specific hook. In 1.3, functions are registered by adding them to a table at the bottom of the module. This causes the problem that every time a new hook is added to the server, modules written for the previous version need to be modified before they will work. Admittedly, this didn't happen often. This scheme also wastes space in the server because every module had the entire module structure declared even though most of the structure was empty. In Apache 2.0, the size of the module structure has shrunk significantly. This is done by replacing most of the structure with one function which allows modules to register functions for the rest of the hooks.
The ability to register individual hooks independent of the rest of the hooks has an important benefit besides saving some memory. In Apache 1.3, all of a module's functions are tied together. This means that if mod_include executes before mod_cgi, then for each hook mod_includes function will execute before mod_cgi's. This restriction has been removed with 2.0. When registering a function in 2.0, it is possible to specify when it should run relative to other modules, either first, last, or in the middle. Any number of modules can register for those positions and within each section the modules are executed in random order. This means that if two modules both register a function for the check_auth hook and they both want their functions to run first, it is impossible to determine which of these two will actually run first. All that is known about those two functions is that they will both run before any function registered to run either last or in the middle. If the module's function must run either before or after another module's function for the same hook, it is also possible to specify that when registering for the hook.
Apache Portable Run-Time
Perhaps the biggest change in Apache 2.0 is the Apache Portable Run-Time (APR). In previous versions of Apache, portability for Apache was handled internally, which kept Apache developers from doing what they really wanted, making the most popular web server. With Apache 2.0, portability is handled by APR. APR is a project that is currently tied to Apache, but should be spun off into its own project soon after the official 2.0 release. The goal of APR is to provide a single C interface to platform- specific functions so that code can be written once and compiled and run everywhere.
This approach has a couple of advantages over handling portability internally. First of all, the Apache code becomes much more manageable and maintainable. Secondly, and more importantly, APR uses native calls whenever possible. As a result, when Apache is running on a Windows system, it looks like a native Windows program, but when Apache is running on a Unix system, it looks like a UNIX program. On Windows this advantage has provided Apache with a major performance boost.
APR has been designed with C programmers in mind. Whenever possible APR functions have been made to mimic POSIX functions in order to make it easy for programmers to quickly port current programs to APR. This has already been done with some of Apache's support programs. For example, ApacheBench, which has never run on Windows, has been ported with minimum effort to all APR-supported platforms including Windows, OS/2, and BeOS.