Revert "internal/coordinator: start VMs without external IPs"

This reverts commit 7e966852b8b669b490c440025b6e4a430b5bfac6 (https://golang.org/cl/354642).

Reason for revert: breaks internet access in -longtest builders somehow

Change-Id: I5344e0c8cec5bf93a23c2c3bf592215843e129de
Reviewed-on: https://go-review.googlesource.com/c/build/+/354753
Run-TryBot: Heschi Kreinick <heschi@google.com>
TryBot-Result: Go Bot <gobot@golang.org>
Reviewed-by: Carlos Amedee <carlos@golang.org>
Reviewed-by: Dmitri Shuralyov <dmitshur@golang.org>
diff --git a/buildlet/gce.go b/buildlet/gce.go
index c508a57..ea10887 100644
--- a/buildlet/gce.go
+++ b/buildlet/gce.go
@@ -71,6 +71,19 @@
 		diskType = "" // a spinning disk
 	}
 
+	// Request an IP address if this is a world-facing buildlet.
+	var accessConfigs []*compute.AccessConfig
+	// TODO(bradfitz): remove the "true ||" part once we figure out why the buildlet
+	// never boots without an IP address. Userspace seems to hang before we get to the buildlet?
+	if true || !opts.TLS.IsZero() {
+		accessConfigs = []*compute.AccessConfig{
+			&compute.AccessConfig{
+				Type: "ONE_TO_ONE_NAT",
+				Name: "External NAT",
+			},
+		}
+	}
+
 	srcImage := "https://www.googleapis.com/compute/v1/projects/" + projectID + "/global/images/" + hconf.VMImage
 	minCPU := hconf.MinCPUPlatform
 	if hconf.IsContainer() {
@@ -113,9 +126,12 @@
 			Items: []string{"https-server"},
 		},
 		Metadata: &compute.Metadata{},
-		NetworkInterfaces: []*compute.NetworkInterface{{
-			Network: prefix + "/global/networks/default-vpc",
-		}},
+		NetworkInterfaces: []*compute.NetworkInterface{
+			&compute.NetworkInterface{
+				AccessConfigs: accessConfigs,
+				Network:       prefix + "/global/networks/default-vpc",
+			},
+		},
 
 		// Prior to git rev 1b1e086fd, we used preemptible
 		// instances, as we were helping test the feature. It was
diff --git a/internal/coordinator/pool/gce.go b/internal/coordinator/pool/gce.go
index d4a40e5..9f70505 100644
--- a/internal/coordinator/pool/gce.go
+++ b/internal/coordinator/pool/gce.go
@@ -321,6 +321,11 @@
 
 var _ Buildlet = (*GCEBuildlet)(nil)
 
+// maxInstances is a temporary hack because we can't get buildlets to boot
+// without IPs, and we only have 200 IP addresses.
+// TODO(bradfitz): remove this once fixed.
+const maxInstances = 190
+
 // GCEBuildlet manages a pool of GCE buildlets.
 type GCEBuildlet struct {
 	mu sync.Mutex // guards all following
@@ -332,6 +337,7 @@
 	instLeft  int // dead-reckoning instances remain
 	instUsage int
 	cpuUsage  int
+	addrUsage int
 	inst      map[string]time.Time // GCE VM instance name -> creationTime
 }
 
@@ -359,6 +365,8 @@
 		case "INSTANCES":
 			p.instLeft = int(quota.Limit) - int(quota.Usage)
 			p.instUsage = int(quota.Usage)
+		case "IN_USE_ADDRESSES":
+			p.addrUsage = int(quota.Usage)
 		}
 	}
 }
@@ -511,7 +519,7 @@
 //
 // precondition: p.mu must be held.
 func (p *GCEBuildlet) haveQuotaLocked(numCPU int) bool {
-	return p.cpuLeft >= numCPU && p.instLeft >= 1
+	return p.cpuLeft >= numCPU && p.instLeft >= 1 && len(p.inst) < maxInstances && p.addrUsage < maxInstances
 }
 
 func (p *GCEBuildlet) tryAllocateQuota(numCPU int) bool {
@@ -524,6 +532,7 @@
 		p.cpuUsage += numCPU
 		p.cpuLeft -= numCPU
 		p.instLeft--
+		p.addrUsage++
 		return true
 	}
 	return false