rewrite User-Name in received Access-Request - tough question :)

Bojan Pogacar bojan at
Sun Oct 28 11:04:44 CET 2012

Hello Alan & Arran.

Alan: I've posted so much garbage solutions, because I wanted to show 
you, that I've tried many things, before writing to this mailing list :)

Arran: I've already tried

update replay {
	User-Name := "%{User-Name}"
} , but CoovaChilly don't honor this and also if It would, I would still 
have to add other Attributes to the replay, like Session-Timeout which 
would be calulated 1800 seconds - seconds allready used.

Alan: Even if UserName rewrite would happen, I could track different 
users by Attribute Calling-Station-Id. I wrote this counter:

sqlcounter dailycountermac {
         counter-name = Daily-Session-Time-Mac
         check-name = Max-Daily-Session-Mac
         reply-name = Session-Timeout
         sqlmod-inst = sql
         key = User-Name
         reset = daily

         query = "SELECT SUM(acctsessiontime - \
                  GREATEST((%b - UNIX_TIMESTAMP(acctstarttime)), 0)) \
                  FROM radacct WHERE username = '%{%k}' AND 
callingstationid = '%{Calling-Station-ID}' AND \
                  UNIX_TIMESTAMP(acctstarttime) + acctsessiontime > '%b'"


I understand now, that this is not a good idea.

I wanted to rewrite username, that I could easily show "Guest" users in 
web application, but I can do that another way.

I will write all the logic in unlang, without username rewrite. I will 
get user parameters with

update reply {
	Session-Timeout := %{sql: SELECT 1800 - SUM(acctsessiontime - \
                  GREATEST((%b - UNIX_TIMESTAMP(acctstarttime)), 0)) \
                  FROM radacct WHERE callingstationid = 
'%{Calling-Station-ID}' AND \
                  UNIX_TIMESTAMP(acctstarttime) + acctsessiontime > '%b'}

.... and so on for bandwidth caping.	

Is there more elegant solution, or this is it?

Thanks again for your help.

Best regards, Bojan

Dne 28.10.2012 10:28, piše Alan DeKok:
> Bojan Pogacar wrote:
>> This is my first post on this mailing list. I hope someone can give me
>> an advice over my problem that I am solving over a month. I even bought
>> a book about freeradius and after reading it twice there is not an
>> answer to my problem.
>    Yes.  Most complicated problems involve putting pieces together.
> Finding a pre-packaged solution is rare.
>> Then they wanted me to change login procedure. All users would get free
>> access for 30 minutes per day and they don't have to login through
>> captive portal. After 30 minutes, captive portal would open and user
>> would have to login with some coupone to connect to the internet.
>    Write this down as workflow for what you want to happen.  When you do
> that, the solution is usually simple.
>    But I do see issues here.  You said some users are authenticated via
> MAC address, and others are not.  If you want to let those others in
> without authenticating to the captive portal, how do you know who they
> are?  How do you track them?
>    That is a big problem.  You WON'T get a user name, because they're not
> using the captive portal.  All you'll get is a MAC address.
>    So you really have two classes of users.  One has a "known MAC", and
> gets full-day access.  So your first priority should be checking for
> those users, and letting them in.  You should also check for non-MAC
> usernames, and authenticate them as you do today.
>    So the only remaining problem is "unknown MAC" users who are trying to
> log in.  Write down what you want in simple English:
>    When an "unknown MAC" user logs in, check their total time usage
> today.  If it's less than 30min, give them up to 30min access.  If it's
> more than 30min, deny them access (or somehow direct them to the captive
> portal).
>> I've solved this by writing these two lines in file "hints"
>> DEFAULT User-Name =~
>> "^[0-9A-F]{2}-[0-9A-F]{2}-[0-9A-F]{2}-[0-9AF]{2}-[0-9A-F]{2}-[0-9A-F]{2}$"
>>         User-Name := "freeinternetfor30minutes"
>    Well, no.  You're talking about an *implementation*.  That's not a
> solution.  The requirements above say nothing about re-writing user names.
>> It worked very well except all users previously authenticated by MAC
>> address didn't get theis own profiles, but they got logged in as
>> "freeinternetfor30minutes" with bandwidth limitations.
>    Exactly.  Because you didn't divide the problem into pieces.
>    Take one piece you know how to solve: "known MAC" users.  If you see a
> login with MAC, check the MAC against a list of "known MAC" users.  If
> it's found, let them in.  Otherwise, do something else.
>    Doing a series of simple checks is MUCH easier than trying to come up
> with one magic rule set which solves all problems.  This is the base of
> the "divide and conquer" strategy.
>> OK, that was logical, I deleted those two lines and wrote some unlung
>> logic to the "sites-available/default"
>>          if(notfound){ #if user not in database
>>                  update reply {
>>                      Reply-Message := "Wrong username or password"
>>                  }
>>          # if username was MAC address, try to login as
>> "freeinternetfor30minutes"
>    Again, there's no need to re-write the User-Name.  It is very, very,
> wrong.
>>                  if (User-Name
>> =~/^([0-9a-f]{2})-([0-9a-f]{2})-([0-9a-f]{2})-([0-9a-f]{2})-([0-9a-f]{2})-([0-9a-f]{2})$/i){
>>                          update reply {
>>                                  Reply-Message := "Hello Guest, I'will
>> try to give you 30 minutes for free, if you didn't allready used it."
>>                          }
>>                          update request{
>>                                  User-Name := "freeinternetfor30minutes"
>>                          }
>    Again, why would this EVER be a good idea?
>>                          update control {
>>                                  Auth-Type := "Accept"
>>                          }
>    You're not setting Session-Timeout.  So they can stay on for as long
> as they want.
>>                  }
>>                 else {
>>                        ok = reject
>>                 }
>    I don't see why this is here.
>> That is working fine, users can connect to the network, BUT accounting
>> section logges their username in database as original MAC address, not
>> rewritted username freeinternetfor30minutes .
>    Yes.  That is a GOOD IDEA.  You need to COMPLETELY FORGET about the
> username "freeinternetfor30minutes".  It's a BAD IDEA.
>> Also no bandwidth
>> limitations arn't sent with Access-Accept, but I think that could be
>> solved easyly.
>    Yes.
>> I've also tries to use module "attr_rewrite". I wrote those lines of
>> code to "modules/attr_rewrite"
>    Why?  You've got the idea to re-write the username.  This makes no
> sense.  It's not part of the requirements.
>    It seems you just randomly chose a particular solution, rather than
> trying to solve the problem piece by piece.
>> and unhashed rewrite_user in "sites-available/default". I see that
>> rewriting does happen, BUT then
>> update control {
>>      Auth-Type := "Accept"
>> }
>> seems to stop working even if I put rewrite_user before "update control"
>    Well, I'm not even going to try to understand that.  The solution is
> wrong, so there's no surprise it doesn't work.
>> AND also in accounting section User-Name is still MAC address, not
>> rewritten username.
>    This is a good thing.
>    How do you expect to track 30min usage per user, when all usernames
> are "freeinternetfor30minutes" ?
>> I am stuck now, without any idea. Can anyone tell me, is this even
>> possible what I am trying to do and if so, what path should I take.
>    It's possible.  The path is very simple.
>> Would it be possible to create new virtual server and pass rewritten
>> username to that virtual server, which would try to login as
>> "freeinternetfor30minutes"
>    Don't do that.  FORGET ABOUT that username.  It is indescribably
> wrong.  It will not solve the problem.  It will CREATE problems.
>    Alan DeKok.
> -
> List info/subscribe/unsubscribe? See

More information about the Freeradius-Users mailing list