instantiate.php 19.1 KB
Newer Older
Leigh B Stoller's avatar
Leigh B Stoller committed
1 2
<?php
#
3
# Copyright (c) 2000-2014 University of Utah and the Flux Group.
Leigh B Stoller's avatar
Leigh B Stoller committed
4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27
# 
# {{{EMULAB-LICENSE
# 
# This file is part of the Emulab network testbed software.
# 
# This file is free software: you can redistribute it and/or modify it
# under the terms of the GNU Affero General Public License as published by
# the Free Software Foundation, either version 3 of the License, or (at
# your option) any later version.
# 
# This file is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
# FITNESS FOR A PARTICULAR PURPOSE.  See the GNU Affero General Public
# License for more details.
# 
# You should have received a copy of the GNU Affero General Public License
# along with this file.  If not, see <http://www.gnu.org/licenses/>.
# 
# }}}
#
chdir("..");
include("defs.php3");
include_once("osinfo_defs.php");
include_once("geni_defs.php");
28
chdir("apt");
Leigh B Stoller's avatar
Leigh B Stoller committed
29
include("quickvm_sup.php");
Leigh B Stoller's avatar
Leigh B Stoller committed
30
include("instance_defs.php");
31
include("profile_defs.php");
Robert Ricci's avatar
Robert Ricci committed
32
$page_title = "Instantiate a Profile";
Leigh B Stoller's avatar
Leigh B Stoller committed
33
$dblink = GetDBLink("sa");
Leigh B Stoller's avatar
Leigh B Stoller committed
34

35 36 37 38 39 40
#
# Get current user but make sure coming in on SSL.
#
RedirectSecure();
$this_user = CheckLogin($check_status);

Leigh B Stoller's avatar
Leigh B Stoller committed
41 42 43
#
# Verify page arguments.
#
44 45 46 47 48 49
$optargs = OptionalPageArguments("create",        PAGEARG_STRING,
				 "profile",       PAGEARG_STRING,
				 "stuffing",      PAGEARG_STRING,
				 "verify",        PAGEARG_STRING,
				 "project",       PAGEARG_PROJECT,
				 "formfields",    PAGEARG_ARRAY,
Leigh B Stoller's avatar
Leigh B Stoller committed
50 51 52 53 54 55 56 57 58
				 "ajax_request",  PAGEARG_BOOLEAN,
				 "ajax_method",   PAGEARG_STRING,
				 "ajax_argument", PAGEARG_STRING);

#
# Deal with ajax requests.
#
if (isset($ajax_request)) {
    if ($ajax_method == "getprofile") {
59 60 61 62 63 64 65 66
	#
	# We require the UUID on this path, until proper permission
	# checks are done; too easy to guess an index.
	#
	if (!IsValidUUID($ajax_argument)) {
	    SPITAJAX_ERROR(1, "Not a valid UUID: $ajax_argument");
	    exit();
	}
67 68 69
	$obj = Profile::Lookup($ajax_argument);
	if (!$obj) {
	    SPITAJAX_ERROR(1, "No such profile $ajax_argument");
Leigh B Stoller's avatar
Leigh B Stoller committed
70 71
	    exit();
	}
72 73 74 75 76 77
	#
	# Need permission checks here.
	#
	SPITAJAX_RESPONSE(array('rspec'       => $obj->rspec(),
				'name'        => $obj->name(),
				'description' => $obj->description()));
Leigh B Stoller's avatar
Leigh B Stoller committed
78 79
    }
    exit();
80

Leigh B Stoller's avatar
Leigh B Stoller committed
81
}
Leigh B Stoller's avatar
Leigh B Stoller committed
82

Robert Ricci's avatar
Robert Ricci committed
83
$profile_default  = "OneVM";
Leigh B Stoller's avatar
Leigh B Stoller committed
84
$profile_array    = array();
85 86 87 88
$am_array = array('Utah DDC' =>
		     "urn:publicid:IDN+utahddc.geniracks.net+authority+cm",
		  'Utah PG'  =>
		     "urn:publicid:IDN+emulab.net+authority+cm");
Leigh B Stoller's avatar
Leigh B Stoller committed
89

90 91 92 93
#
# if using the super secret URL, make sure the profile exists, and
# add to the array now since it might not be public or belong to the user.
#
94
if (isset($profile)) {
95 96
    #
    # Guest users must use the uuid, but logged in users may use the
97 98 99
    # internal index. But, we have to support simple the URL too, which
    # is /p/project/profilename, but only for public profiles. Need to
    # deal with the version at some point.
100
    #
101 102 103 104 105 106 107
    if (isset($project) && isset($profile)) {
	$obj = Profile::LookupByName($project, $profile);
    }
    elseif ($this_user || IsValidUUID($profile)) {
	$obj = Profile::Lookup($profile);
    }
    else {
108 109 110 111 112 113 114 115
	SPITUSERERROR("Illegal profile for guest user: $profile");
	exit();
    }
    if (! $obj) {
	SPITUSERERROR("No such profile: $profile");
	exit();
    }
    if (IsValidUUID($profile)) {
116 117 118 119
	$profile_array[$profile] = $obj->name();
	$profilename = $obj->name();
    }
    else {
120 121 122 123
	#
	# Must be public or belong to user. 
	#
	if (! ($obj->ispublic() ||
124
	       $obj->creator_idx() == $this_user->uid_idx())) {
125 126 127 128 129 130
	    SPITUSERERROR("No permission to use profile: $profile");
	    exit();
	}
	$profile = $obj->uuid();
	$profile_array[$profile] = $obj->name();
	$profilename = $obj->name();
131
    }
132 133
}

134
#
135 136 137
# Find all the public and user profiles. We use the UUID instead of
# indicies cause we do not want to leak internal DB state to guest
# users.
138
#
Leigh B Stoller's avatar
Leigh B Stoller committed
139
$query_result =
140 141 142
    DBQueryFatal("select * from apt_profiles ".
		 "where public=1 " .
		 ($this_user ? "or creator_idx=" . $this_user->uid_idx() : ""));
Leigh B Stoller's avatar
Leigh B Stoller committed
143
while ($row = mysql_fetch_array($query_result)) {
144
    $profile_array[$row["uuid"]] = $row["name"];
145
    if ($row["pid"] == $TBOPSPID && $row["name"] == $profile_default) {
146
	$profile_default = $row["uuid"];
147
    }
148
    if (isset($profile)) {
149
        # Look for the profile by project/name and switch to uuid.
150 151 152
	if (isset($project) &&
	    $row["pid"] == $project->pid() &&
	    $row["name"] == $profile) {
153
	    $profile = $row["uuid"];
154
	}
155
    }
Leigh B Stoller's avatar
Leigh B Stoller committed
156
}
Leigh B Stoller's avatar
Leigh B Stoller committed
157

158
function SPITFORM($formfields, $newuser, $errors)
Leigh B Stoller's avatar
Leigh B Stoller committed
159 160
{
    global $TBBASE, $TBMAIL_OPS;
161
    global $profile_array, $this_user, $profilename, $profile, $am_array;
Leigh B Stoller's avatar
Leigh B Stoller committed
162

163 164 165
    # XSS prevention.
    while (list ($key, $val) = each ($formfields)) {
	$formfields[$key] = CleanString($val);
Leigh B Stoller's avatar
Leigh B Stoller committed
166
    }
167
    # XSS prevention.
Leigh B Stoller's avatar
Leigh B Stoller committed
168
    if ($errors) {
169
	while (list ($key, $val) = each ($errors)) {
170 171 172 173 174
	    # Skip internal error, we want the html in those errors
	    # ands we know it is safe.
	    if ($key == "error") {
		continue;
	    }
175
	    $errors[$key] = CleanString($val);
Leigh B Stoller's avatar
Leigh B Stoller committed
176 177
	}
    }
178 179 180 181 182 183 184 185 186 187 188 189 190 191 192

    $formatter = function($field, $html) use ($errors) {
	$class = "form-group";
	if ($errors && array_key_exists($field, $errors)) {
	    $class .= " has-error";
	}
	echo "<div class='$class'>\n";
	echo "     $html\n";
	if ($errors && array_key_exists($field, $errors)) {
	    echo "<label class='control-label' for='inputError'>" .
		$errors[$field] . "</label>\n";
	}
	echo "</div>\n";
    };

Leigh B Stoller's avatar
Leigh B Stoller committed
193
    SPITHEADER(1);
Leigh B Stoller's avatar
Leigh B Stoller committed
194

195
    echo "<div class='row'>
Leigh B Stoller's avatar
Leigh B Stoller committed
196
          <div class='col-lg-6  col-lg-offset-3
197
                      col-md-6  col-md-offset-3
Leigh B Stoller's avatar
Leigh B Stoller committed
198 199
                      col-sm-8  col-sm-offset-2
                      col-xs-12 col-xs-offset-0'>\n";
Jonathon Duerig's avatar
Jonathon Duerig committed
200 201 202

    SpitAboutApt();

203
    echo "<form id='quickvm_form' role='form'
204
            enctype='multipart/form-data'
205
            method='post' action='instantiate.php'>\n";
206 207 208
    echo "<div class='panel panel-default'>
           <div class='panel-heading'>
              <h3 class='panel-title'>
209 210 211 212 213
              Run an Experiment";
    if (isset($profilename)) {
        echo " using profile &quot;$profilename&quot";
    }
    echo "</h3></div>
214
           <div class='panel-body'>\n";
215 216 217 218 219
    
    #
    # If linked to a specific profile, description goes here
    #
    if ($profile) {
220
        # Note: Following line is also duplicated below
221 222 223 224
        echo "  <span class='' style='display: inline-block; margin-bottom: 10px'
                      id='selected_profile_description'></span>\n";
    }

225 226 227 228 229 230
    echo "   <fieldset>\n";

    #
    # Look for non-specific error.
    #
    if ($errors && array_key_exists("error", $errors)) {
231 232
	echo "<font color=red><center>" . $errors["error"] .
	    "</center></font><br>";
233
    }
234 235 236 237

    #
    # Ask for user information
    #
238 239 240 241 242 243 244 245 246 247 248 249
    if (!isset($this_user)) {
	$formatter("username", 
		  "<input name=\"formfields[username]\"
		          value='" . $formfields["username"] . "'
                          class='form-control'
                          placeholder='Pick a user name'
                          autofocus type='text'>");
   
	$formatter("email", 
		  "<input name=\"formfields[email]\"
                          type='text'
                          value='" . $formfields["email"] . "'
250
                          class='form-control'
251
                          placeholder='Your email address' type='text'>");
Keith Downie's avatar
Keith Downie committed
252

253 254 255 256 257
	$formatter("keyfile",
		   "<span class='help-block'>
                     SSH Public Key (choose file or paste in)</span>".
		   "<input type=file name='keyfile'>");

258 259
	$formatter("sshkey", 
		  "<textarea name=\"formfields[sshkey]\" 
260
                             placeholder='Paste in your ssh public key.'
261 262 263 264
                             class='form-control'
                             rows=4 cols=45>" . $formfields["sshkey"] .
                  "</textarea>");
    }
265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285

    #
    # Only print profile selection box if we weren't linked to a specific
    # profile
    #
    if (!isset($profile)) {
        echo "<div id='profile_well' class='form-group well well-md'>
                <span id='selected_profile_text' class='pull-left'>
                </span>
                <input id='selected_profile' type='hidden' 
                       name='formfields[profile]'/>
                  <button id='profile' class='btn btn-primary btn-xs pull-right' 
                         type='button' name='profile_button'>
                    Select a Profile
                  </button>\n";
        if ($errors && array_key_exists("profile", $errors)) {
            echo "<label class='control-label' for='inputError'>" .
                $errors["profile"] .
                " </label>\n";
        }
        echo " </div>\n";
286
        # Note: Following line is also duplicated above
287 288
        echo "  <span class=''
                      id='selected_profile_description'></span>\n";
289
    }
Leigh B Stoller's avatar
Leigh B Stoller committed
290
    else {
291 292 293 294 295 296 297
	echo "<input id='selected_profile' type='hidden'
                     name='formfields[profile]'
                     value='" . $formfields["profile"] . "'>\n";

	# Send the original argument for the initial array stuff above.
        # Needs more work.
	echo "<input type='hidden' name='profile' value='$profile'>\n";
Leigh B Stoller's avatar
Leigh B Stoller committed
298
    }
299 300 301 302 303 304 305 306 307 308 309 310 311 312 313
    if (isset($this_user) && ISADMIN()) {
	$am_options = "";
	while (list($am, $urn) = each($am_array)) {
	    $selected = "";
	    if ($formfields["where"] == $am) {
		$selected = "selected";
	    }
	    $am_options .= 
		"<option $selected value='$am'>$am</option>\n";
	}
	$formatter("where",
		   "<br><select name=\"formfields[where]\"
		              id='profile_where' class='form-control'>".
		   "$am_options</select>");
    }
314
    echo "</fieldset>
315
           <button class='btn btn-success pull-right' id='instantiate_submit'
Keith Downie's avatar
Keith Downie committed
316
              type='submit' name='create'>Create!
317 318
           </button>
           <br> 
319 320 321
        </div>
        </div>
        </div>
Leigh B Stoller's avatar
Leigh B Stoller committed
322
        </div>\n";
323 324
    if (!isset($this_user)) {
	SpitVerifyModal("verify_modal", "Create");
325
    
326 327 328 329 330 331 332 333
	if ($newuser) {
	    if (is_string($newuser)) {
		$stuffing = $newuser;
	    }
	    else {
		$stuffing = substr(GENHASH(), 0, 16);
	    }
	    mail($formfields["email"],
334
		 "aptlab.net: Verification code for creating your experiment",
335 336 337 338 339
		 "Here is your user verification code. Please copy and\n".
		 "paste this code into the box on the experiment page.\n\n".
		 "      $stuffing\n",
		 "From: $TBMAIL_OPS");
	    echo "<input type='hidden' name='stuffing' value='$stuffing' />";
Leigh B Stoller's avatar
Leigh B Stoller committed
340 341 342 343
	}
    }
    echo "</form>\n";

344
    SpitTopologyViewModal("quickvm_topomodal", $profile_array);
345
    SpitWaitModal("waitwait");
Keith Downie's avatar
Keith Downie committed
346

347
    echo "<script type='text/javascript'>\n";
348
    echo "    window.PROFILE = '" . $formfields["profile"] . "';\n";
349 350 351 352
    if ($newuser) {
	echo "window.APT_OPTIONS.isNewUser = true;\n";
    }
    echo "</script>\n";
353
    echo "<script src='js/lib/require.js' data-main='js/instantiate'></script>";
Leigh B Stoller's avatar
Leigh B Stoller committed
354 355 356
}

if (!isset($create)) {
357 358 359 360 361
    $defaults = array();
    $defaults["username"] = "";
    $defaults["email"]    = "";
    $defaults["sshkey"]   = "";
    $defaults["profile"]  = (isset($profile) ? $profile : $profile_default);
362
    $defaults["where"]    = 'Utah DDC';
363
	
364
    # 
365
    # Look for current user or cookie that tells us who the user is. 
366
    #
367
    if ($this_user) {
368 369
	$defaults["username"] = $this_user->uid();
	$defaults["email"]    = $this_user->email();
370 371
    }
    elseif (isset($_COOKIE['quickvm_user'])) {
Leigh B Stoller's avatar
Leigh B Stoller committed
372 373 374 375 376 377
	$geniuser = GeniUser::Lookup("sa", $_COOKIE['quickvm_user']);
	if ($geniuser) {
	    #
	    # Look for existing quickvm. User not allowed to create
	    # another one.
	    #
Leigh B Stoller's avatar
Leigh B Stoller committed
378 379 380
	    $instance = Instance::LookupByCreator($geniuser->uuid());
	    if ($instance && $instance->status() != "terminating") {
		header("Location: status.php?uuid=" . $instance->uuid());
Leigh B Stoller's avatar
Leigh B Stoller committed
381 382
		return;
	    }
383 384 385
	    $defaults["username"] = $geniuser->name();
	    $defaults["email"]    = $geniuser->email();
	    $defaults["sshkey"]   = $geniuser->SSHKey();
Leigh B Stoller's avatar
Leigh B Stoller committed
386 387
	}
    }
388
    SPITFORM($defaults, false, array());
Leigh B Stoller's avatar
Leigh B Stoller committed
389 390 391 392 393 394 395 396 397
    SPITFOOTER();
    return;
}
#
# Otherwise, must validate and redisplay if errors
#
$errors = array();
$args   = array();

398 399 400 401
if (!$this_user) {
    #
    # These check do not matter for a logged in user; we ignore the values.
    #
402
    if (!isset($formfields["email"]) || $formfields["email"] == "") {
403 404
	$errors["email"] = "Missing Field";
    }
405
    elseif (! TBvalid_email($formfields["email"])) {
406 407
	$errors["email"] = TBFieldErrorString();
    }
408
    if (!isset($formfields["username"]) || $formfields["username"] == "") {
409 410
	$errors["username"] = "Missing Field";
    }
411
    elseif (! TBvalid_uid($formfields["username"])) {
412 413
	$errors["username"] = TBFieldErrorString();
    }
414
    elseif (User::LookupByUid($formfields["username"])) {
415
        # Do not allow uid overlap with real users.
416
	$errors["username"] = "Already in use - if you have an Emulab account, log in first";
417
    }
Leigh B Stoller's avatar
Leigh B Stoller committed
418
}
419
if (!isset($formfields["profile"]) || $formfields["profile"] == "") {
Leigh B Stoller's avatar
Leigh B Stoller committed
420
    $errors["profile"] = "No selection made";
Leigh B Stoller's avatar
Leigh B Stoller committed
421
}
422 423
elseif (! array_key_exists($formfields["profile"], $profile_array)) {
    $errors["profile"] = "Invalid Profile: " . $formfields["profile"];
Leigh B Stoller's avatar
Leigh B Stoller committed
424 425 426 427 428
}

#
# More sanity checks. 
#
429 430 431 432 433 434 435 436 437
if ($this_user) {
    if (! $this_user->HasEncryptedCert(1)) {
	$url = CreateURL("gensslcert", $this_user);
    
	$errors["error"] = "Oops, registered Emulab users must create a ".
	    "<a href='$TBBASE/$url'>ssl certificate</a> first";
    }
}
else {
438
    $geniuser = GeniUser::LookupByEmail("sa", $formfields["email"]);
439
    if ($geniuser) {
440
	if ($geniuser->name() != $formfields["username"]) {    
441 442 443
	    $errors["email"] = "Already in use by another user";
	    unset($geniuser);
	}
Leigh B Stoller's avatar
Leigh B Stoller committed
444 445
    }
}
446

447 448 449 450 451 452 453 454 455 456 457 458 459 460 461 462
#
# Allow admin users to select the Aggregate. Experimental.
#
$aggregate_urn = "";

if ($this_user && ISADMIN()) {
    if (isset($formfields["where"]) && $formfields["where"] != "") {
	if (array_key_exists($formfields["where"], $am_array)) {
	    $aggregate_urn = $am_array[$formfields["where"]];
	}
	else {
	    $errors["where"] = "Invalid Aggregate";
	}
    }
}

463 464 465 466 467 468
if (count($errors)) {
    SPITFORM($formfields, false, $errors);
    SPITFOOTER();
    return;
}

469 470
#
# SSH keys are now optional for guest users; they just have to
471 472 473 474
# use the web based ssh window.
#
# Backend verifies pubkey and returns error. We first look for a 
# file and then fall back to an inline field.
475
#
476 477 478 479 480 481 482 483
if (isset($_FILES['keyfile']) &&
    $_FILES['keyfile']['name'] != "" &&
    $_FILES['keyfile']['name'] != "none") {

    $localfile = $_FILES['keyfile']['tmp_name'];
    $args["sshkey"] = file_get_contents($localfile);
}
elseif (isset($formfields["sshkey"]) && $formfields["sshkey"] != "") {
484
    $args["sshkey"] = $formfields["sshkey"];
Leigh B Stoller's avatar
Leigh B Stoller committed
485 486 487
}

if (count($errors)) {
488
    SPITFORM($formfields, false, $errors);
Leigh B Stoller's avatar
Leigh B Stoller committed
489 490 491
    SPITFOOTER();
    return;
}
492
# Silently ignore the form for a logged in user. 
493 494 495
$args["username"] = ($this_user ? $this_user->uid() : $formfields["username"]);
$args["email"]    = ($this_user ? $this_user->email() : $formfields["email"]);
$args["profile"]  = $formfields["profile"];
Leigh B Stoller's avatar
Leigh B Stoller committed
496 497 498 499 500

#
# See if user exists and is verified. We send email with a code, which
# they have to paste back into a box we add to the form. See above.
#
Leigh B Stoller's avatar
Leigh B Stoller committed
501 502 503 504 505
# We also get here if the user exists, but the browser did not have
# the tokens, as will happen if switching to another browser. We
# force the user to repeat the verification with the same code we
# have stored in the DB.
#
506 507 508
if (!$this_user &&
    (!$geniuser || !isset($_COOKIE['quickvm_authkey']) ||
     $_COOKIE['quickvm_authkey'] != $geniuser->auth_token())) {
Leigh B Stoller's avatar
Leigh B Stoller committed
509 510
    if (isset($stuffing) && $stuffing != "") {
	if (! (isset($verify) && $verify == $stuffing)) {
511
	    SPITFORM($formfields, $stuffing, $errors);
Leigh B Stoller's avatar
Leigh B Stoller committed
512 513 514
	    SPITFOOTER();
	    return;
	}
Leigh B Stoller's avatar
Leigh B Stoller committed
515 516 517 518 519
	#
	# If this is an existing user and they give us the right code,
	# we can check again for an existing VM and redirect to the
	# status page, like we do above.
	#
520
	if ($geniuser) {
Leigh B Stoller's avatar
Leigh B Stoller committed
521 522 523
	    $instance = Instance::LookupByCreator($geniuser->uuid());
	    if ($instance && $instance->status() != "terminating") {
		header("Location: status.php?uuid=" . $instance->uuid());
Leigh B Stoller's avatar
Leigh B Stoller committed
524 525 526
		return;
	    }
	}
Leigh B Stoller's avatar
Leigh B Stoller committed
527 528 529 530
	# Pass to backend to save in user object.
	$args["auth_token"] = $stuffing;
    }
    else {
Leigh B Stoller's avatar
Leigh B Stoller committed
531 532
	# Existing user, use existing auth token.
	# New user, we create a new one.
533
	$token = ($geniuser ? $geniuser->auth_token() : true);
Leigh B Stoller's avatar
Leigh B Stoller committed
534

535
	SPITFORM($formfields, $token, $errors);
Leigh B Stoller's avatar
Leigh B Stoller committed
536 537 538 539 540
	SPITFOOTER();
	return;
    }
}

Leigh B Stoller's avatar
Leigh B Stoller committed
541
#
Leigh B Stoller's avatar
Leigh B Stoller committed
542
# This is so we can look up the slice after the backend creates it.
Leigh B Stoller's avatar
Leigh B Stoller committed
543 544 545
# We tell the backend what uuid to use.
#
$quickvm_uuid = NewUUID();
Leigh B Stoller's avatar
Leigh B Stoller committed
546 547 548 549 550 551 552 553 554 555 556 557 558 559 560 561 562 563 564 565 566 567 568 569 570

#
# Generate a temporary file and write in the XML goo. 
#
$xmlname = tempnam("/tmp", "quickvm");
if (! $xmlname) {
    TBERROR("Could not create temporary filename", 0);
    $errors["internal"] = "Transient error(1); please try again later.";
}
elseif (! ($fp = fopen($xmlname, "w"))) {
    TBERROR("Could not open temp file $xmlname", 0);
    $errors["internal"] = "Transient error(2); please try again later.";
}
else {
    fwrite($fp, "<quickvm>\n");
    foreach ($args as $name => $value) {
	fwrite($fp, "<attribute name=\"$name\">");
	fwrite($fp, "  <value>" . htmlspecialchars($value) . "</value>");
	fwrite($fp, "</attribute>\n");
    }
    fwrite($fp, "</quickvm>\n");
    fclose($fp);
    chmod($xmlname, 0666);
}
if (count($errors)) {
571
    SPITFORM($formfields, false, $errors);
Leigh B Stoller's avatar
Leigh B Stoller committed
572 573 574 575 576 577 578 579 580 581 582
    SPITFOOTER();
    return;
}

#
# Invoke the backend. This will create the user and the slice record
# in the SA database, and then fork off in the background. If the
# first part works, we can return to the user and use some nifty ajax
# and javascript to watch for progress. We use a cookie that holds
# the slice uuid so that the JS code can ask about it.
#
583 584
# This option is used to tell the backend that it is okay to look
# in the emulab users table.
Leigh B Stoller's avatar
Leigh B Stoller committed
585
#
586 587 588
if (isset($_SERVER['REMOTE_ADDR'])) { 
    putenv("REMOTE_ADDR=" . $_SERVER['REMOTE_ADDR']);
}
589 590
$opt  = ($this_user ? "-l" : "");
$opt .= ($aggregate_urn != "" ? " -a '$aggregate_urn'" : "");
591

Leigh B Stoller's avatar
Leigh B Stoller committed
592 593
$retval = SUEXEC("nobody", "nobody",
		 "webquickvm $opt -u $quickvm_uuid $xmlname",
Leigh B Stoller's avatar
Leigh B Stoller committed
594
		 SUEXEC_ACTION_CONTINUE);
Leigh B Stoller's avatar
Leigh B Stoller committed
595 596 597

if ($retval != 0) {
    if ($retval < 0) {
598
	$errors["error"] = "Transient error(3); please try again later.";
Leigh B Stoller's avatar
Leigh B Stoller committed
599 600 601 602
    }
    else {
	if (count($suexec_output_array)) {
	    $line = $suexec_output_array[$i];
603
	    $errors["error"] = $line;
Leigh B Stoller's avatar
Leigh B Stoller committed
604 605
	}
	else {
606
	    $errors["error"] = "Transient error(4); please try again later.";
Leigh B Stoller's avatar
Leigh B Stoller committed
607 608
	}
    }
609
    SPITFORM($formfields, false, $errors);
Leigh B Stoller's avatar
Leigh B Stoller committed
610 611 612 613 614
    SPITFOOTER();
    return;
}
unlink($xmlname);

Leigh B Stoller's avatar
Leigh B Stoller committed
615 616
$instance = Instance::Lookup($quickvm_uuid);
if (!$instance) {
617 618
    $errors["error"] = "Transient error(5); please try again later.";
    SPITFORM($formfields, false, $errors);
Leigh B Stoller's avatar
Leigh B Stoller committed
619 620 621
    SPITFOOTER();
    return;
}
622 623 624 625
if ($this_user) {
    $creator = $this_user;
}
else {
Leigh B Stoller's avatar
Leigh B Stoller committed
626
    $creator = GeniUser::Lookup("sa", $instance->creator_uuid());
627
}
Leigh B Stoller's avatar
Leigh B Stoller committed
628
if (! $creator) {
629 630
    $errors["error"] = "Transient error(6); please try again later.";
    SPITFORM($formfields, false, $errors);
Leigh B Stoller's avatar
Leigh B Stoller committed
631 632 633
    SPITFOOTER();
    return;
}
634
#
Leigh B Stoller's avatar
Leigh B Stoller committed
635
# Remember the user and auth key so that we can verify.
636 637 638 639 640 641
#
# The cookie handling is a pain since we run this under the aptlab
# virtual host, but the config uses a different domain, and so the
# cookies do not work. So, we have to look at our SERVER_NAME and
# set the cookie appropriately. 
#
642
if (!$this_user) {
Leigh B Stoller's avatar
Leigh B Stoller committed
643 644
    $cookiedomain = $TBAUTHDOMAIN;

645 646 647 648 649 650
    setcookie("quickvm_user",
	      $creator->uuid(), time() + (24 * 3600 * 30),
	      "/", $cookiedomain, 0);
    setcookie("quickvm_authkey",
	      $creator->auth_token(), time() + (24 * 3600 * 30),
	      "/", $cookiedomain, 0);
651
}
Leigh B Stoller's avatar
Leigh B Stoller committed
652
header("Location: status.php?uuid=" . $instance->uuid());
Leigh B Stoller's avatar
Leigh B Stoller committed
653
?>