Re: SQL help from someone who groks c, please?

2007-02-08 Thread ChristosH



Phil Mayers wrote:
 
 Dan Mahoney, System Admin wrote:
 
 My suggestion is that you use a custom schema and queries for your 
 database - probably a stored procedure. Pass the NAS-IP-Address into 
 these queries, and return different values based on the nas. Effectively 
 you move the code that walks over the request and chooses the right 
 values into the SQL server.
 

So if I was looking to select a different response based on NAS what I
should be doing is creating a stored procedure that ends up authenticating
for me? I don't quite see where this would fit in with the rlm_sql logic. 
Would that go in the sql.conf file? For using a new schema, would that mean
instead adding an extra column in the radcheck table and the response table
to associate with the NAS IP?

Would it be easier to create a function that inserts a prefex to the user
name then processes the SQL as normal? The only issue I see with this is
doubling the amount of users and user responses in the database .

Either way, I think i'm going to have to modify the rlm_sql.c file and then
having to recompile FreeRadius after I'm done editing it?
-- 
View this message in context: 
http://www.nabble.com/SQL-help-from-someone-who-groks-c%2C-please--tf3172009.html#a8870617
Sent from the FreeRadius - User mailing list archive at Nabble.com.

- 
List info/subscribe/unsubscribe? See http://www.freeradius.org/list/users.html


Re: SQL help from someone who groks c, please?

2007-02-08 Thread Dan Mahoney, System Admin
On Thu, 8 Feb 2007, ChristosH wrote:


No, wrong.

You can include any %{check-item} in your query.  I didn't have to modify 
the code at all, but my queries are PERVERSE.  Yours will probably be 
simpler.

If you want to give me your proposed database setup and schema, and what 
you need to auth against, I might be able to offer you a quick answer.  If 
it's a longer and more involved thing, contact me off-list and I might be 
able to work something for you.

This is my auth query (which is actually two) (beware, it's for our site 
database which polls a 
LOT of info from different tables you won't need -- however I find this to 
be a far more real-world example than dedicated radius tables) -- You can 
see that in this case I manually insert the Password Attribute, and 
Operator by using string literals.

authorize_check_query=\
SELECT `adm_permissions`.`admPermitID` AS `id`, 
`adm_permissions`.`admp_username` AS `UserName`, 'Password' as Attribute, 
\
`adm_permissions`.`admp_password` AS `Value`, '==' as Op FROM 
`adm_permissions` , `switches` Inner Join `interface_ip` ON \
`switches`.`id` = `interface_ip`.`deviceid` WHERE admp_username = 
'%{SQL-User-Name}' AND \
`interface_ip`.`interface_is_primary` = '1' AND \
interface_address = '%{NAS-IP-Address}'

This above gets permissions for any staff user, and checks our one-to-many 
interface table to find out what device they're actually logging into.

UNION SELECT IPCustomerID as id, 
`ip_customer`.`ipc_rmtusername`, 'Password' as \
Attribute,\
`ip_customer`.`ipc_rmtpassword` as Value, '==' as Op FROM `ip_customer` 
Inner Join `interface_ip` ON \
`ip_customer`.`ipc_rmtip` = `interface_ip`.`interface_address` Inner Join 
`switches` ON `switches`.`id` = \
`interface_ip`.`deviceid` WHERE interface_address = '%{NAS-IP-Address}' 
AND ipc_rmtusername = '%{SQL-User-Name}' \
GROUP BY `ip_customer`.`ipc_rmtusername`,\
`interface_ip`.`interface_address`

This does the same for any customer user.

Then my reply-items

authorize_reply_query = SELECT `ip_customer`.`ipCustomerID` AS `id`, 
`ip_customer`.`ipc_rmtusername` AS UserName,\
`rad_reply`.`Attribute`,`rad_reply`.`Value`, `rad_reply`.`Op` FROM 
`ip_customer` Left Join `interface_ip` ON \
`ip_customer`.`ipc_rmtip` =`interface_ip`.`interface_address` Inner Join 
`switches` ON `switches`.`id` = \
`interface_ip`.`deviceid` Inner Join`rad_reply` ON `switches`.`role` = 
`rad_reply`.`devicetype` WHERE \
`rad_reply`.`Usertype` = '2' AND ipc_rmtusername ='%{SQL-User-Name}' and 
interface_address = '%{NAS-IP-Address}' group by \
ipc_rmtusername, interface_address


This only lets a customer in if it has a devicetype of 2 (which is a 
remote reboot unit AND if they are listed as having a device on that unit. 
We have a table that specifies if you are a customer user then your reply 
is Outlet  If you're staff then it's Admin-User.

UNION 
SELECT`adm_permissions`.`admPermitID` AS `id`, 
`adm_permissions`.`admp_username` \
AS `UserName`, `rad_reply`.`Attribute`,`rad_reply`.`Value`, 
`rad_reply`.`Op` FROM `adm_permissions` , `switches` Inner \
Join `interface_ip` ON `switches`.`id` =`interface_ip`.`deviceid` Inner 
Join `rad_reply` ON `switches`.`role` = \
`rad_reply`.`devicetype` WHERE`rad_reply`.`Usertype` = '1' AND 
admp_username = '%{SQL-User-Name}' and interface_address = \
'%{NAS-IP-Address}'

Do the same as above with staff.

UNION SELECT `remote`.`port`as id, 
`ip_customer`.`ipc_rmtusername` as UserName, _latin1 \
'APC-Outlets' as Attribute,group_concat(remote.port order by remote.port 
asc separator ',') as Value, _latin1 ':=' as \
Op FROM `remote` Inner Join`ip_customer` ON `remote`.`suite` = 
`ip_customer`.`ipc_suite` AND `remote`.`row` = \
`ip_customer`.`ipc_row` AND`remote`.`rack` = `ip_customer`.`ipc_rack` AND 
`remote`.`server` = `ip_customer`.`ipc_server` \
Inner Join `interface_ip` ON`remote`.`deviceid` = 
`interface_ip`.`deviceid` Inner Join `switches` ON remote.deviceid = \
switches.id WHERE`ip_customer`.`ipc_rmtreboot` = 'y' AND 
ip_customer.ipc_rmtusername = '%{SQL-User-Name}' AND ipc_rmtip = \
'%{NAS-IP-Address}' AND switches.role = '4' GROUP BY interface_address, 
`ip_customer`.`ipc_rmtusername`

If they are a customer, return a comma-separated list of which outlets 
they 
are authorized for. (See the APC radius spec).






 Phil Mayers wrote:

 Dan Mahoney, System Admin wrote:

 My suggestion is that you use a custom schema and queries for your
 database - probably a stored procedure. Pass the NAS-IP-Address into
 these queries, and return different values based on the nas. Effectively
 you move the code that walks over the request and chooses the right
 values into the SQL server.


 So if I was looking to select a different response based on NAS what I
 should be doing is creating a stored procedure that ends up authenticating
 for me? I don't quite see where this would fit in with the rlm_sql logic.
 Would that go in the sql.conf file? For using a new schema, would that mean
 instead adding an 

Re: SQL help from someone who groks c, please?

2007-02-08 Thread Dan Mahoney, System Admin
On Thu, 8 Feb 2007, ChristosH wrote:



 Phil Mayers wrote:

 A stored procedure is one solution to a particular set of problems.
 Whether it's appropriate depends on what you're trying to do.

 What do you want to achieve? You can certainly vary the reply info based
 on NAS without a stored procedure.


 Well, what I want to do is return a different vendor specific response based
 on the NAS IP.  The user data doesn't change depending on the NAS IP, but
 depending on where the user tries to authenticate from they'll have a
 different source NAS IP in the authenticate request packet and my response
 has to return a different response depending on where they are. Right now I
 have only 2 different responses that they could be, so I don't think it
 should be too difficult. Is there a quick workaround?

Okay, so create a table with your NASes, include the IP adderss, include a 
type flag.

Create another table with the responses for each type, join to the query 
on the type flag.  Use those responses.

-Dan

--

A mother can be an inspiration to her little son, change his thoughts,
his mind, his life, just with her gentle hum.

-No Doubt, Different People, from Tragic Kingdom


Dan Mahoney
Techie,  Sysadmin,  WebGeek
Gushi on efnet/undernet IRC
ICQ: 13735144   AIM: LarpGM
Site:  http://www.gushi.org
---

- 
List info/subscribe/unsubscribe? See http://www.freeradius.org/list/users.html


Re: SQL help from someone who groks c, please?

2007-02-05 Thread Phil Mayers
Dan Mahoney, System Admin wrote:
 
 I assume you mean the core SQL module, and nothing driver specific, yes?

Yep. The relevant code is in rlm_sql.c so it's driver-independent.

 
 However, in the CVS version of FreeRadius, the SQL code works much more
 like you'd expect:
 
 Also, for the edification of anyone who might stumble on this, the CVS 
 code relevant to which version?  I.e. would this be a 2.x branch thing? 

Sorry my bad - should have been more precise. The code I am looking at 
is a checkout of HEAD. I'm not familiar with the dev/release plans for 
2.0 - hopefully one of the devs will chip in here.

 advanced examples if need be.  The concept of group ownership is still 
 good, but with SQL working the way you describe, and fall-through working 
 right, it's not strictly as necessary as it was: in theory it's possible 
 with the new code to select ALL rows, and read the whole table just like 
 an old-style users-file, no (waste of processor and resources aside).

Very good point - removing the where username= bit from the group 
membership query would return each group in turn (ordered by precedence).

 
 ...with appropriate check/reply items (e.g. check item might be
 huntgroup or nas-ip-address). The groups would contain one user - in the
 previous example, jeremy.
 
 Okay -- do you know anything about if the semicolon is intentionally 
 ignored?  I tried doing multiple queries in a single statement but got an 
 error (thank god for UNION).

I hazily recall a discussion w.r.t. MySQL and (I think) the 
SQL_MULTI_STATEMENT option not being on in the driver, but here we reach 
the limit of my knowledge. As far as I can tell from the source, rlm_sql 
just passes the xlat'ed string to the driver, so any handling of lack 
therefore of multiple statements would be in there.

 
 -Dan
 
 --
 
 Dan Mahoney
 Techie,  Sysadmin,  WebGeek
 Gushi on efnet/undernet IRC
 ICQ: 13735144   AIM: LarpGM
 Site:  http://www.gushi.org
 ---
 
 - 
 List info/subscribe/unsubscribe? See http://www.freeradius.org/list/users.html

- 
List info/subscribe/unsubscribe? See http://www.freeradius.org/list/users.html


Re: SQL help from someone who groks c, please?

2007-02-05 Thread Peter Nixon
On Mon 05 Feb 2007 10:56, Phil Mayers wrote:
 Dan Mahoney, System Admin wrote:
  I assume you mean the core SQL module, and nothing driver specific, yes?

 Yep. The relevant code is in rlm_sql.c so it's driver-independent.

  However, in the CVS version of FreeRadius, the SQL code works much more
  like you'd expect:
 
  Also, for the edification of anyone who might stumble on this, the CVS
  code relevant to which version?  I.e. would this be a 2.x branch thing?

 Sorry my bad - should have been more precise. The code I am looking at
 is a checkout of HEAD. I'm not familiar with the dev/release plans for
 2.0 - hopefully one of the devs will chip in here.

Hopefully soon! I am pushing Alan to release in the near future, and I think 
he is coming around :-)

I have been running CVS head in production for close to 6 months now and we 
have successfully closed all the bugs that have affected me (Zero memory 
leaks or crashes this month. Yay!).

I run rlm_sql_postgresql, rlm_acctlog, rlm_exec, radrelay, rlm_sqlippool and 
rlm_detail in a fairly complex, high volume setup including a number of 
proxy servers. I am still doing minor cleanups and feature additions on 
rlm_sqlippool but I have moved it to the stable modules list as it has 
proven itself (at least in my setup on postgresql).

Oh, I also us attribute filters pre and post proxy.. (They rock!)

I will be turning some attention onto rlm_python this week also as I want to 
put it into production on a couple of servers.

Cheers
-- 

Peter Nixon
http://www.peternixon.net/
PGP Key: http://www.peternixon.net/public.asc


pgpLwnLeG28zI.pgp
Description: PGP signature
- 
List info/subscribe/unsubscribe? See http://www.freeradius.org/list/users.html

Re: SQL help from someone who groks c, please?

2007-02-04 Thread Dan Mahoney, System Admin
On Mon, 5 Feb 2007, Phil Mayers wrote:

 Dan Mahoney, System Admin wrote:

 That said, I figured out two possible ways to handle my previous question
 regarding advanced SQL auth (including multiple occurances of the same

 Minor point of terminology - SQL doesn't authenticate. It acts as a
 store for config and reply items.

Of course.  I myself am in the habit of stating things I already know to 
be true, just for the advantage of some poor soul trying to get something 
from mailing list archives.

 Not in the current server.

 Neither of your examples will work, because cCurrently* in the release
 version of FreeRadius, rlm_sql works as follows:

  * select per-user check items from radcheck
  * select all group check items for that user from radgroupcheck
  * merge them
  * compare them - if match:
* select per-user reply items from radreply
* select all group reply items for that user from radgroupreply
* merge them
* add them to the reply

 Because of the merging of the check/reply items, with the currently
 release version of FreeRadius it will be difficult to achieve what you
 want. There are probably ways to use clever tricks with the schema, but
 the algorithm that iterates over the SQL results is coded into the C
 portion of the module, and is not really flexible enough.

I assume you mean the core SQL module, and nothing driver specific, yes?

 My suggestion is that you use a custom schema and queries for your
 database - probably a stored procedure. Pass the NAS-IP-Address into
 these queries, and return different values based on the nas. Effectively
 you move the code that walks over the request and chooses the right
 values into the SQL server.

This I'm already doing.  I just wanted to be sure I wasn't going about it 
wrong.

 However, in the CVS version of FreeRadius, the SQL code works much more
 like you'd expect:

Also, for the edification of anyone who might stumble on this, the CVS 
code relevant to which version?  I.e. would this be a 2.x branch thing? 
Note that I'm not asking the luserish when will it be out I need it 
now!!!1 question, as I've already got workarounds in place to do what I 
need, but I've come across threads dating back five years in some software 
and was never sure which version was relevant.

  * select per-user check items from radcheck
  * compare them
  * if match, add per-user reply items from radreply
  * if Fall-Through:
* for each group
  * select per-group check items
  * compare them
  * if match, add the per-group reply items
  * stop unless Fall-Through

 With that schema, it would be relatively trivial to (ab)use groups as
 users.

Or I'd join against my devices table and return one entry for jeremy 
based on each network device in the grid with a simple left join (the 
distinction being that it's multiple answers based on a less-specific 
question, as opposed to a single check-item based on a more-specific 
query.)  Again, my SQL know-how is good, so I can contrib some more 
advanced examples if need be.  The concept of group ownership is still 
good, but with SQL working the way you describe, and fall-through working 
right, it's not strictly as necessary as it was: in theory it's possible 
with the new code to select ALL rows, and read the whole table just like 
an old-style users-file, no (waste of processor and resources aside).

For example, right now I have a few tables that match user-type and device 
type, so that for any user type, and any device (say, cisco core routers, 
or extreme distribution switches), that lists the appropriate reply-items.

The annoyance and minor difference here is the requirement to specialize 
the query -- with the current code, I need to include anything I want to 
specialize on (which means if there's five different check-items, I have 
to include them (and not all devices will include such check-items).

No groups necessary (I am not using them now, in fact, my queries 
encompass that logic).

 ...with appropriate check/reply items (e.g. check item might be
 huntgroup or nas-ip-address). The groups would contain one user - in the
 previous example, jeremy.

Okay -- do you know anything about if the semicolon is intentionally 
ignored?  I tried doing multiple queries in a single statement but got an 
error (thank god for UNION).

-Dan

--

Dan Mahoney
Techie,  Sysadmin,  WebGeek
Gushi on efnet/undernet IRC
ICQ: 13735144   AIM: LarpGM
Site:  http://www.gushi.org
---

- 
List info/subscribe/unsubscribe? See http://www.freeradius.org/list/users.html