In putting together a mechanism for handling authentication and accounting with a Cisco Voice Gateway, such as the AS5350XM, I came across the ACE RADIUS Library. It is self described as a free, open source portable RADIUS stack.
The stack uses ACE_Task for basic network communication.
ACE
is a very good and well respected C++ network
programming framework. I've started doing an few projects with it.
Anyway, ace-radius comes as a zip file, rather than a .gz file, so remember to unzip it
into a directory, otherwise the 'current' directory may get polluted with files.
When building, the ACE library is required, and the environment variable ACE_ROOT needs
to be set to where the ACE_wrappers directory resides. Before compiling a couple of fixes
for the current version of the compiler are required:
- CRadiusPacket.h, line 291: friend class CRadiusAttribute;
- CRadiusClientStack.h, line 109: friend class CRadiusClientConnection;
- CRadiusAttribute.cpp, line 455, 479, 1084, 1097: s/.S_un.S_addr/.s_addr/
- CRadiusClientConnection.cpp, line 65: ACE::set_flags(m_socket.get_handle(), O_NONBLOCK);
Instead of using the existing Makefiles, I copied all the source files from their various
directories into a single directory under Eclipse and compiled them into a single library.
I excluded the Client and Server test directories.
A number of good examples are provided, which show both the client and server sides.
The API is quite clean and useful. Good doxygen documentation is supplied.
I was quite impressed with how easy it was to accept an authentication request, and reply
with an accept or a deny packet.
The Radius server I'm writing is but one component of several inter-communicating network
components for talking with a voice gateway, authenticating and rating calls, collecting
call detail records, passing along realtime call information, and presenting the realtime
call status in a browser.
For the other inter-communicating components, I had them fleshed out with the
ACE_Connector and ACE_Acceptor Frameworks.
I got to the point where I needed to rework my
Wt web server/client with the
ACE Framework.
However, there became a bit of an issue. Wt uses ASIO for its network communications. This
put
me into a quandary. Recent reading is indicating that ASIO, which now comes natively in the
latest Boost release of 1.35.0, is more C++'sh than is ACE. I see that there is also much
overlap in Boost
and ACE, at least from the concepts I might need to use: message passing, threading,
inter-process communications, network communications, etc.
In ACE, I see a strength with its Service Configuration Framework and its Naming Service.
With the distributed components I'm writing, the mentioned frameworks would come in handy
for provisioning and service enablement.
However, at this point in time, I'm thinking of migrating to the ASIO/Boost way of
doing things. I'll put off thinking about the service configuration and naming stuff for
a little later. Hooefully I'll come across something suitable in the meantime.
The ACE framework is flexible and complicated, and something I was willing to negotiate
my way through. But when I see a lot of learning needed to wend my way through the Boost
libraries as well, I think I'll use Boost where I can, and then wrap ACE in something when
forced to work with it.
Which brings me back to the Ace-Radius library. I may be able to port a couple of key
ACE based classes to ASIO and not have to worry about ACE. If not, then I'll set the ACE
based
classes in a thread for acting as a Radius server, run another thread for ASIO to
communicate with my other network objects, and then have the ACE thread forward stuff to the
ASIO thread for communicating with the rest of my infrastructure.