use PVE::Cluster qw(cfs_read_file cfs_write_file cfs_register_file cfs_lock_file);
use PVE::Tools;
use JSON;
-use NetAddr::IP;
+use NetAddr::IP qw(:lower);
+
use Net::IP;
use Digest::SHA;
}
sub add_ip {
- my ($class, $plugin_config, $subnetid, $subnet, $ip, $hostname, $description, $is_gateway) = @_;
+ my ($class, $plugin_config, $subnetid, $subnet, $ip, $hostname, $mac, $description, $is_gateway) = @_;
my $cidr = $subnet->{cidr};
my $zone = $subnet->{zone};
cfs_lock_file($ipamdb_file, undef, sub {
my $db = read_db();
-
my $dbzone = $db->{zones}->{$zone};
die "zone '$zone' doesn't exist in IPAM DB\n" if !$dbzone;
my $dbsubnet = $dbzone->{subnets}->{$cidr};
die "subnet '$cidr' doesn't exist in IPAM DB\n" if !$dbsubnet;
- die "IP '$ip' already exist\n" if defined($dbsubnet->{ips}->{$ip});
-
- $dbsubnet->{ips}->{$ip} = {
- hostname => $hostname,
- description => $description,
- };
+ die "IP '$ip' already exist\n" if (!$is_gateway && defined($dbsubnet->{ips}->{$ip})) || ($is_gateway && defined($dbsubnet->{ips}->{$ip}) && !defined($dbsubnet->{ips}->{$ip}->{gateway}));
+ $dbsubnet->{ips}->{$ip} = {};
+ $dbsubnet->{ips}->{$ip} = {gateway => 1} if $is_gateway;
write_db($db);
});
die "$@" if $@;
}
+sub update_ip {
+ my ($class, $plugin_config, $subnetid, $subnet, $ip, $hostname, $mac, $description, $is_gateway) = @_;
+ return;
+}
+
sub add_next_freeip {
- my ($class, $plugin_config, $subnetid, $subnet, $hostname, $description) = @_;
+ my ($class, $plugin_config, $subnetid, $subnet, $hostname, $mac, $description) = @_;
my $cidr = $subnet->{cidr};
my $network = $subnet->{network};
die "cannot find free IP in subnet '$cidr'\n" if defined($dbsubnet->{ips}->{$network});
$freeip = $network;
} else {
- my $iplist = new NetAddr::IP($cidr);
- my $broadcast = $iplist->broadcast();
-
+ my $iplist = NetAddr::IP->new($cidr);
+ my $lastip = $iplist->last()->canon();
+ $iplist++ if Net::IP::ip_is_ipv4($network); #skip network address for ipv4
while(1) {
- $iplist++;
- last if $iplist eq $broadcast;
- my $ip = $iplist->addr();
- next if defined($dbsubnet->{ips}->{$ip});
+ my $ip = $iplist->canon();
+ if (defined($dbsubnet->{ips}->{$ip})) {
+ last if $ip eq $lastip;
+ $iplist++;
+ next;
+ }
$freeip = $ip;
last;
}
die "can't find free ip in subnet '$cidr'\n" if !$freeip;
- $dbsubnet->{ips}->{$freeip} = {
- hostname => $hostname,
- description => $description,
- };
+ $dbsubnet->{ips}->{$freeip} = {};
write_db($db);
});