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.

converting dotted quad ip to longip?

Help for those learning Tcl or writing their own scripts.
Post Reply
User avatar
rosc2112
Revered One
Posts: 1454
Joined: Sun Feb 19, 2006 8:36 pm
Location: Northeast Pennsylvania

converting dotted quad ip to longip?

Post by rosc2112 »

After reading a post in the egghelp forum about the "longip" used in eggdrop's logs for dcc chat connects, I did a little research and came across a bit of code to convert longip to dotted quad's, and vice versa. However, the piece called "inet_addr" that's supposed to convert dotted quad ip's to longip's doesn't seem to use the same base, or something. I'm not familiar with the 'binary' command well enough to figure this out.

Here's the relevent piece of code:

Code: Select all

# convert dotted quad ip to long ip
proc inet_addr { ipaddr } {
        set addr [binary format c4 [split $ipaddr .]]
        binary scan $addr i bin
        return $bin
}
The other segment is called inet_ntoa:

Code: Select all

# convert long ip to dotted quad ip
proc inet_ntoa { ipaddr } {
        set bin [binary format i $ipaddr]
        binary scan $bin cccc a b c d
        set a [expr { ($a + 0x100) % 0x100 }]
        set b [expr { ($b + 0x100) % 0x100 }]
        set c [expr { ($c + 0x100) % 0x100 }]
        set d [expr { ($d + 0x100) % 0x100 }]
        #
        # Note: this is what was in the original, it presents the dotted quad ip *backwards*...
        # I don't know if that is how inet_ntoa normally behaves -rosc
        #return "$a.$b.$c.$d"
        #
        # So, for my purposes, I present the dotted quad ip in the right order.
        return "$d.$c.$b.$a"
}
When I take a longip from eggdrop's log, and run it through the inet_ntoa, that works just fine, I get my dotted quad IP back as it should.

But, if I then take my dotted quad IP and try to run it through the inet_addr proc, it produces a number nowhere near the number eggdrop uses in its log.

For example:

<rosc> .long2quad 3473389373 (this is the number in eggdrop's log)
<TheEntity> Long IP To Dotted Quad IP: 207.7.183.61

<rosc> .quad2long 207.7.183.61
<TheEntity> Dotted Quad IP To Long IP: 1035405263

Curiously, if I then run that longip back through, I get my ip back, backwards:

<rosc> .long2quad 1035405263
<TheEntity> Long IP To Dotted Quad IP: 61.183.7.207

My question is, how to fix the proc inet_addr thing to give me the same longip number that eggdrop itself uses? I'm guessing that the proc as written, uses a different base than what eggdrop is using.

BTW, I found the above bits of code here:
http://www.mail-archive.com/aolserver@l ... 02599.html
User avatar
demond
Revered One
Posts: 3073
Joined: Sat Jun 12, 2004 9:58 am
Location: San Francisco, CA
Contact:

Post by demond »

Code: Select all

proc n2a {n} {
   foreach i {24 16 8 0} {append s [format %d. [expr ($n>>$i)&0xFF]]}
   return [string trimright $s .]
}
proc a2n {s} {
   foreach {a b c d} [split $s .] {return [expr 0xFFFFFFFF&(($a<<24)+($b<<16)+($c<<8)+$d)]}
}
connection, sharing, dcc problems? click <here>
before asking for scripting help, read <this>
use

Code: Select all

 tag when posting logs, code
User avatar
user
&nbsp;
Posts: 1452
Joined: Tue Mar 18, 2003 9:58 pm
Location: Norway

Post by user »

demond wrote:

Code: Select all

proc a2n {s} {
   foreach {a b c d} [split $s .] {return [expr 0xFFFFFFFF&(($a<<24)+($b<<16)+($c<<8)+$d)]}
}
try

Code: Select all

a2n 128.0.0.0
(if the number is treated as a signed 32 bit integer, you'll get an overflow for ips >= 128.0.0.0) you need to format the output to be an unsigned int (format %u)

Here's a couple of procs doing the same thing without expr :P

Code: Select all

proc dec2dot dec {
	join [scan [format %08x $dec] %2x%2x%2x%2x] .
}
proc dot2dec dot {
	format %u [eval format 0x%02x%02x%02x%02x [split $dot .]]
}
Have you ever read "The Manual"?
User avatar
rosc2112
Revered One
Posts: 1454
Joined: Sun Feb 19, 2006 8:36 pm
Location: Northeast Pennsylvania

Post by rosc2112 »

Sweet. Thanks demond & user :)
User avatar
demond
Revered One
Posts: 3073
Joined: Sat Jun 12, 2004 9:58 am
Location: San Francisco, CA
Contact:

Post by demond »

as ever, user has the more elegant solution ;)

nevertheless, the [expr] version is correct as is:

Code: Select all

% a2n 128.0.0.0
2147483648
% n2a 2147483648
128.0.0.0
masking with 0xffffffff does the format %u trick
connection, sharing, dcc problems? click <here>
before asking for scripting help, read <this>
use

Code: Select all

 tag when posting logs, code
User avatar
user
&nbsp;
Posts: 1452
Joined: Tue Mar 18, 2003 9:58 pm
Location: Norway

Post by user »

demond wrote:masking with 0xffffffff does the format %u trick
format %u is the only way to make it work in tcl <= 8.3.2 (and possibly even higher versions) - i don't know when they changed this, but this page suggests a variant of the problem is still present in 8.4.3

Code: Select all

% info patchlevel
8.3.2
% a2n 128.0.0.0
-2147483648
Have you ever read "The Manual"?
Post Reply