8

In that program I want to increment IP address. And I see output like that:

125.23.45.67
126.23.45.67
127.23.45.67 
128.23.45.67
129.23.45.67
130.23.45.67
131.23.45.67
132.23.45.67
133.23.45.67
134.23.45.67

But I want to see output like this:

124.23.45.67
124.23.45.68
124.23.45.68 
124.23.45.70
124.23.45.71
124.23.45.72
124.23.45.73
124.23.45.74
124.23.45.75
124.23.45.76

Here is program code:

#include <stdlib.h>
#include <stdio.h>
#include <iostream>
using namespace std;
#include "winsock2.h"
#pragma comment(lib,"wsock32.lib")

void main()
{
in_addr adr1;
in_addr adr2;
int i;

adr1.s_addr=inet_addr("124.23.45.67");
adr2.s_addr=inet_addr("as.34.34.56");
if (adr1.s_addr!=INADDR_NONE)
    cout << " adr1 correct" << endl;
else
    cout << " adr1 incorect " << endl;

if (adr2.s_addr!=INADDR_NONE)
    cout << " adr2 correct" << endl;
else
    cout << " adr2 incorect" << endl;

cout << inet_ntoa(adr1) << endl;
cout << inet_ntoa(adr2) << endl;

for (i=0;i<10;i++)
{
    adr1.s_addr ++;
    cout << inet_ntoa(adr1) << endl;
}
}
bortzmeyer
  • 34,164
  • 12
  • 67
  • 91
d_pilot
  • 309
  • 1
  • 3
  • 12

3 Answers3

20

Big endian and little endian gets another one! Use htonl and ntohl to convert back and forth.

for (i=0;i<10;i++)
{
    adr1.s_addr  = htonl(ntohl(adr1.s_addr) + 1);

    cout << inet_ntoa(adr1) << endl;
}
selbie
  • 100,020
  • 15
  • 103
  • 173
  • +1, but flipping the byte ordering seems hackish. [Other people](http://stackoverflow.com/questions/1505676/how-do-i-increment-an-ip-address-represented-as-a-string/1505709#1505709) agree with you, though. –  Jul 19 '11 at 07:30
  • 1
    Doing "math" on an IP address seems odd anyway. What happens when the math generates an IP address off the subnet? All the corner cases have to be handled. – selbie Jul 19 '11 at 07:45
  • 2
    A bit of history. Back in the 90's, when Sun ruled the Unix planet with their Sparc architecture. No one would properly use the endian conversion functions because they didn't need to. Then Linux on x86 came around the same time as Winsock. It was really annoying to port network code to these new platforms- because it would compile just fine, but not actually work. – selbie Jul 19 '11 at 07:48
  • @selbie: doing math on a pointer seems odd. What happens when the math generates a pointer off the array? And yet... ;-) – Steve Jessop Jul 19 '11 at 08:50
  • I mean a pointer (http://en.wikipedia.org/wiki/Pointer_%28computing%29#C_and_C.2B.2B). People do math on them, despite the fact that this math could exceed valid bounds. It's the responsibility of the person doing the math to avoid this. In this IP address example, if you know that the subnet mask is at least 7 bits then the range x.y.z.67 to x.y.z.76 is not off the subnet. – Steve Jessop Jul 19 '11 at 09:46
  • This works fine. But, how to avoid generating network and broadcast addresses ? – w00t May 31 '12 at 11:37
  • The OP never really said what he was trying to do, so I gave him a very specific answer for the problem he was trying to solve. My golden rule of socket and network programming: The developer should have good knowledge on the fundamentals of TCP/IP before attempting to write such code. – selbie May 31 '12 at 19:37
5

To increment an IP address you will need to break up the in_addr object into 4 int objects (a short int will also do) and increment the 4th one until it hits 256, and then reset it to 1 and increment the 3rd one, etc. You shouldn't be using ++ on the in_addr object directly.

EDIT: Okay, so you can properly increment it if you reverse the byte order. I personally wouldn't do it that way. Especially if all you're doing is outputting IP strings and not using them as an in_addr elsewhere in code.

2

Instead of using adr1.s_addr:

adr1.s_addr=inet_addr("124.23.45.67");
adr2.s_addr=inet_addr("as.34.34.56"); 

Use this:

u_long addr1=inet_addr("124.23.45.67");

And increment addr1, i.e. addr1++ the last octet gets incremented.

Or follow this formula:

if IP is A.B.C.D then u_long addr = A + 256*B + 256*256*C + 256*256*256*D
Ilia Ross
  • 13,086
  • 11
  • 53
  • 88