This is the new home of the egghelp.org community forum.
All data has been migrated (including user logins/passwords) to a new phpBB version.


For more information, see this announcement post. Click the X in the top right-corner of this box to dismiss this message.

[Solved] Formating ip's: CIDR to dotted?

Help for those learning Tcl or writing their own scripts.
Post Reply
G
Garp
Voice
Posts: 29
Joined: Mon Sep 15, 2003 7:58 pm

[Solved] Formating ip's: CIDR to dotted?

Post by Garp »

I wrote a little tcl script to do a whois lookup on a certain ip like 10.43.8.67 and return the country and the ip-range.

If the ip-range is in the format "10.43.8.64 - 10.43.8.79" everything is ok, I can turn the ips into longips and store them for later lookups in a mysql db.

But sometimes the whois lookup returns CIDR formated values like 10.43.8.67/28 and I don't know on which way I can calculate the dotted ip range. Could somebody help?

My code at the moment:

Code: Select all


if {[namespace exists ::ip2nation]} {namespace delete ::ip2nation}
namespace eval ::ip2nation {

	namespace export dowhois

	variable whoisbin [lindex [split [exec which whois]] 0]
	
	variable version 0.1

	variable rp; array set rp {
		inetnum {(?ni)inetnum: (.*)}
		country {(?ni)country: (.*)}	
	}
	
	putlog "\00312$rp(inetnum)\003";



	proc dowhois {uhost} {

		if [regexp {[0-9]{1,3}.[0-9]{1,3}.[0-9]{1,3}.[0-9]{1,3}$} $uhost] {



            if {[catch {set lookup [eval exec $::ip2nation::whoisbin $uhost]} xError] != 0} {
                return -code error "Error calling whois:  ($::ip2nation::whoisbin $uhost): $xError"
            }
            
            
			foreach line [split [string trim [regsub -all {;(.+?)\n} $lookup {}]] \n] {
			if {![string length $line]} {continue}
			

                if [string match "*inetnum*" $line] {
                    regexp $::ip2nation::rp(inetnum) $line {} netblock
                    putlog "\00304netblock [string trim $netblock]\003";
                    if [string match "*/*" $rep] {
                    
# here I am lost, I could start a perl script to calculate the ip but that's not what I want.
                    
                    }
                }           

                if [string match "*country*" $line] {
                    regexp $::ip2nation::rp(country) $line {} country
                    putlog "\00304country [string trim $country]\003";
                    
                }

	
			}           

            
            
        } else {
        
        	dnslookup $uhost dns_test
        
        }
	}


     proc dns_test {ip uhost status} {

     	dowhois $ip

     }


}

package provide ip2nation $::ip2nation::version

putlog "\00304ip2nation.tcl v$::iptnation:version\003 "

Last edited by Garp on Sun Dec 24, 2006 4:27 pm, edited 1 time in total.
G
Garp
Voice
Posts: 29
Joined: Mon Sep 15, 2003 7:58 pm

Post by Garp »

Ok, found a solution for that. Just for the records here the way on retriving the range of ips on a given CIDR (Classless Inter-Domain Routing) ip like 190.40.112.0/25

Code: Select all

  
                  set max_ip [expr ($min_ip + round(pow(2, [expr 32 - $subnetmask]))) - 1]

Subnetmask is the part after / in CIDR.

The formula returns a long_ip. The min_ip is already in the CIDR format (190.40.112.0) and has to be turned into long_ip format for being calculated.

We get 190.40.112.0/25 is 3190321152 - 3190321279 or 190.40.112.0 - 190.40.112.127.
User avatar
rosc2112
Revered One
Posts: 1454
Joined: Sun Feb 19, 2006 8:36 pm
Location: Northeast Pennsylvania

Post by rosc2112 »

Cool.. I had thought about making a cidr calculator for tcl, having plenty of em in perl and other script languages, but few in tcl (most of which that I've seen didn't have as many features as their perl counterparts, and also needed tk)

I'd love to see someone make a full-featured cidr/network calculator for tcl/eggdrop :)
Post Reply