Commit d0b403f7 authored by Leigh B. Stoller's avatar Leigh B. Stoller

Beef up Create() routine, used from the Protogeni cooked mode to

create "proxy" nodes for remote geni nodes.

Clean up method access to reserved table slots.

Changes/Fixes to CreateVnodes() to support cooked mode Protogeni
nodes.
parent b8a25ce0
......@@ -253,6 +253,11 @@ sub AUTOLOAD {
#
# Create a new node.
#
# The list of table we have to clear if anything goes wrong.
my @cleantables = ("nodes", "node_hostkeys", "node_status",
"node_activity", "node_utilization",
"node_auxtypes", "reserved", "widearea_nodeinfo");
sub Create($$$$)
{
my ($class, $node_id, $experiment, $argref) = @_;
......@@ -286,30 +291,56 @@ sub Create($$$$)
print STDERR "*** No virtnode_capacity for $type! Using zero.\n";
$virtnode_capacity = 0;
}
if ($typeinfo->adminmfs_osid(\$adminmfs_osid)) {
print STDERR "*** No adminmfs osid for $type!\n";
return undef;
}
# Find object for the adminfs.
if (defined($adminmfs_osid)) {
$adminmfs = OSinfo->Lookup($adminmfs_osid);
if ($isremote) {
$osid = 0;
$opmode = "";
if (defined($typeinfo->default_osid())) {
$osid = $typeinfo->default_osid();
my $osinfo = OSinfo->Lookup($osid);
if (!defined($osinfo)) {
print STDERR
"*** Could not find OSinfo object for $osid!\n";
return undef;
}
$osid = $osinfo->osid();
$opmode = $osinfo->op_mode();
}
}
else {
$adminmfs = OSinfo->Lookup(TBOPSPID(), $MFS_INITIAL);
}
if (!defined($adminmfs)) {
print STDERR "*** Could not find OSinfo object for adminmfs!\n";
return undef;
if ($typeinfo->adminmfs_osid(\$adminmfs_osid)) {
print STDERR "*** No adminmfs osid for $type!\n";
return undef;
}
# Find object for the adminfs.
if (defined($adminmfs_osid)) {
$adminmfs = OSinfo->Lookup($adminmfs_osid);
}
else {
$adminmfs = OSinfo->Lookup(TBOPSPID(), $MFS_INITIAL);
}
if (!defined($adminmfs)) {
print STDERR
"*** Could not find OSinfo object for adminmfs!\n";
return undef;
}
$osid = $adminmfs->osid();
$opmode = $adminmfs->op_mode();
}
$osid = $adminmfs->osid();
$opmode = $adminmfs->op_mode();
}
else {
$osid = 0;
$opmode = "";
}
$state = $STATE_INITIAL;
#
# Lock the tables to prevent concurrent creation
#
DBQueryWarn("lock tables nodes write, widearea_nodeinfo write")
or return -1;
#
# Make up a priority (just used for sorting)
#
......@@ -319,21 +350,35 @@ sub Create($$$$)
else {
$priority = 1;
}
# The list of table we have to clear if anything goes wrong.
my @cleantables = ("nodes", "node_hostkeys", "node_status",
"node_activity", "node_utilization",
"node_auxtypes", "reserved");
DBQueryWarn("insert into nodes set ".
" node_id='$node_id', type='$type', " .
" phys_nodeid='$node_id', role='$role', ".
" priority=$priority, " .
" eventstate='$state', op_mode='$opmode', " .
" def_boot_osid='$osid', " .
" inception=now(), uuid=$uuid, ".
" state_timestamp=unix_timestamp(NOW()), " .
" op_mode_timestamp=unix_timestamp(NOW())")
or goto bad;
if (!DBQueryWarn("insert into nodes set ".
" node_id='$node_id', type='$type', " .
" phys_nodeid='$node_id', role='$role', ".
" priority=$priority, " .
" eventstate='$state', op_mode='$opmode', " .
" def_boot_osid='$osid', " .
" inception=now(), uuid=$uuid, ".
" state_timestamp=unix_timestamp(NOW()), " .
" op_mode_timestamp=unix_timestamp(NOW())")) {
DBQueryWarn("unlock tables");
return undef;
}
if ($isremote) {
my $hostname = $argref->{'hostname'};
my $external = $argref->{'external_node_id'};
my $IP = $argref->{'IP'};
if (!DBQueryWarn("replace into widearea_nodeinfo ".
" (node_id, contact_uid, contact_idx, hostname," .
" external_node_id, IP) ".
" values ('$node_id', 'nobody', '0', ".
" '$hostname', '$external', '$IP')")) {
DBQueryWarn("delete from nodes where node_id='$node_id'");
DBQueryWarn("unlock tables");
return undef;
}
}
DBQueryWarn("unlock tables");
if ($role eq "testnode") {
DBQueryWarn("insert into node_hostkeys (node_id) ".
......@@ -399,6 +444,20 @@ sub Create($$$$)
return undef;
}
#
# Only use this for Create() errors.
#
sub Delete($)
{
my ($self) = @_;
my $node_id = $self->node_id();
foreach my $table (@cleantables) {
DBQueryWarn("delete from $table where node_id='$node_id'");
}
return 0;
}
#
# Refresh a class instance by reloading from the DB.
#
......@@ -984,43 +1043,29 @@ sub HasVirtualNodes($)
return $query_result->numrows;
}
# Need to create a set of access methods for the reservation.
sub vname($)
{
my ($self) = @_;
return undef
if (! ref($self));
return undef
if (! $self->IsReserved());
return $self->{"RSRV"}->{'vname'};
}
sub sharing_mode($)
#
# Access methods for the reservation.
#
sub __reservation($$)
{
my ($self) = @_;
my ($self, $slotname) = @_;
return undef
if (! ref($self));
return undef
if (! $self->IsReserved());
return $self->{"RSRV"}->{'sharing_mode'};
}
sub erole($)
{
my ($self) = @_;
return undef
if (! ref($self));
if (! exists($self->{"RSRV"}->{$slotname}));
return undef
if (! $self->IsReserved());
return $self->{"RSRV"}->{'erole'};
return $self->{"RSRV"}->{$slotname};
}
sub vname($) { return __reservation($_[0], 'vname'); }
sub sharing_mode($) { return __reservation($_[0], 'sharing_mode'); }
sub erole($) { return __reservation($_[0], 'erole'); }
sub external_resource_index($) {
return __reservation($_[0], 'external_resource_index'); }
sub external_resource_id($) {
return __reservation($_[0], 'external_resource_id'); }
#
# Lookup a specific attribute in the node_attributes table,
......@@ -1174,7 +1219,8 @@ sub Update($$)
my $val = $argref->{$key};
# Treat NULL special.
push (@sets, "${key}=" . ($val eq "NULL" ? "NULL" : "'$val'"));
push (@sets, "${key}=" . ($val eq "NULL" ?
"NULL" : DBQuoteSpecial($val)));
}
my $query = "update nodes set " . join(",", @sets) .
......@@ -1534,8 +1580,9 @@ sub CreateVnodes($$)
print STDERR "*** CreateVnodes: Not a dynamic node type: '$vtype'\n";
return -1;
}
my $isremote = $nodetype->isremotenode();
my $isjailed = $nodetype->isjailed();
my $isremote = $nodetype->isremotenode();
my $isjailed = $nodetype->isjailed();
my $isfednode = $nodetype->isfednode();
#
# Make up a priority (just used for sorting). We need the name prefix
......@@ -1544,7 +1591,13 @@ sub CreateVnodes($$)
my $nodeprefix;
my $nodenum;
my $ipbase;
if ($pnode =~ /^(.*\D)(\d+)$/) {
if ($isfednode) {
$nodeprefix = $nodetype->type();
$nodenum = "";
$ipbase = 0;
}
elsif ($pnode =~ /^(.*\D)(\d+)$/) {
$nodeprefix = $1;
$nodenum = $2;
$ipbase = $nodenum;
......@@ -1553,25 +1606,29 @@ sub CreateVnodes($$)
$nodeprefix = $pnode;
$nodenum = "";
#
# Determine ipbase from the control IP.
#
my $interface = Interface->LookupControl($node);
if (!defined($interface)) {
print STDERR "*** CreateVnodes: No control interface for $node\n";
return -1;
}
my $ctrlip = $interface->IP();
if (!defined($ctrlip) || $ctrlip eq "") {
print STDERR "*** CreateVnodes: No control IP for $interface\n";
return -1;
}
my $tmp = ~inet_aton($CONTROL_NETMASK) & inet_aton($ctrlip);
$ipbase = unpack("N", $tmp);
if ($ipbase == 0 || $ipbase < 0 || $ipbase > 0x3fff) {
print STDERR
"*** CreateVnodes: Bad ipbase '$ipbase' for $interface\n";
return -1;
if ($isjailed) {
#
# Determine ipbase from the control IP (jailed nodes).
#
my $interface = Interface->LookupControl($node);
if (!defined($interface)) {
print STDERR
"*** CreateVnodes: No control interface for $node\n";
return -1;
}
my $ctrlip = $interface->IP();
if (!defined($ctrlip) || $ctrlip eq "") {
print STDERR
"*** CreateVnodes: No control IP for $interface\n";
return -1;
}
my $tmp = ~inet_aton($CONTROL_NETMASK) & inet_aton($ctrlip);
$ipbase = unpack("N", $tmp);
if ($ipbase == 0 || $ipbase < 0 || $ipbase > 0x3fff) {
print STDERR
"*** CreateVnodes: Bad ipbase '$ipbase' for $interface\n";
return -1;
}
}
}
......@@ -1632,7 +1689,7 @@ sub CreateVnodes($$)
$node->FlushReserved();
my $sharing_mode = $node->sharing_mode();
if (!$impotent) {
if (! ($impotent || $isfednode)) {
my $reservation = $node->Reservation();
if (!defined($reservation)) {
print STDERR "*** CreateVnodes: no reservation for $node!\n";
......@@ -1688,33 +1745,36 @@ sub CreateVnodes($$)
#
# Create a bunch.
#
foreach my $i (@tocreate) {
my $vpriority = 10000000 + ($ipbase * 1000) + $i;
my $vnodeid = $nodeprefix . "vm" . $nodenum . "-" . $i;
#
# Construct the vnode IP. The general form is:
# <IPBASE1>.<IPBASE2>.<pnode>.<vnode>
# but if <pnode> is greater than 254 we have to increment
# IPBASE2.
#
# XXX at Utah our second big cluster of nodes starts at
# nodenum=201 and I would like our vnode IPs to align
# at that boundary, so 254 becomes 200.
#
my $nodenumlimit = $ISUTAH ? 200 : 254;
my $pnet = $IPBASE2;
my $pnode2 = int($ipbase);
while ($pnode2 > $nodenumlimit) {
$pnet++;
$pnode2 -= $nodenumlimit;
foreach my $n (@tocreate) {
my $vpriority = 10000000 + ($ipbase * 1000) + $n;
my $vnodeid = $nodeprefix . "vm" . $nodenum . "-" . $n;
my $jailip;
if ($isjailed) {
#
# Construct the vnode IP. The general form is:
# <IPBASE1>.<IPBASE2>.<pnode>.<vnode>
# but if <pnode> is greater than 254 we have to increment
# IPBASE2.
#
# XXX at Utah our second big cluster of nodes starts at
# nodenum=201 and I would like our vnode IPs to align
# at that boundary, so 254 becomes 200.
#
my $nodenumlimit = $ISUTAH ? 200 : 254;
my $pnet = $IPBASE2;
my $pnode2 = int($ipbase);
while ($pnode2 > $nodenumlimit) {
$pnet++;
$pnode2 -= $nodenumlimit;
}
$jailip = "${IPBASE1}.${pnet}.${pnode2}.${n}";
}
my $jailip = "${IPBASE1}.${pnet}.${pnode2}.${i}";
# Need to keep the UUIDs consistent across regression mode.
my $uuid;
if ($regression) {
$uuid = "${pnode2}${i}-1111-2222-3333-44444444";
$uuid = "0000${n}-1111-2222-3333-44444444";
}
else {
$uuid = (@uuids ? shift(@uuids) : NewUUID());
......@@ -1725,7 +1785,9 @@ sub CreateVnodes($$)
}
if ($verbose) {
print STDERR "Jail IP for $vnodeid is $jailip\n";
print STDERR "Jail IP for $vnodeid is $jailip\n"
if ($jailip);
if ($impotent) {
print STDERR
"Would allocate $vnodeid on $pnode ($vtype, $osid)\n";
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment