runsc: use a pipe for the NAT blob

This is just a little easier than creating and deleting a temp file.

PiperOrigin-RevId: 578575893
This commit is contained in:
Kevin Krakauer
2023-11-01 11:11:36 -07:00
committed by gVisor bot
parent f28e39a2c4
commit c011b6ad79
3 changed files with 12 additions and 19 deletions
-3
View File
@@ -451,9 +451,6 @@ func (n *Network) CreateLinksAndRoutes(args *CreateLinksAndRoutesArgs, _ *struct
// Set NAT table rules if necessary.
if args.NATBlob {
log.Infof("Replacing NAT table")
if _, err := unix.Seek(int(args.FilePayload.Files[fdOffset].Fd()), 0, unix.SEEK_SET); err != nil {
return fmt.Errorf("failed to seek: %v", err)
}
iptReplaceBlob, err := io.ReadAll(args.FilePayload.Files[fdOffset])
if err != nil {
return fmt.Errorf("failed to read iptables blob: %v", err)
+1 -2
View File
@@ -322,11 +322,10 @@ func createInterfacesAndRoutesFromNS(conn *urpc.Client, nsPath string, conf *con
// Pass the host's NAT table if requested.
if conf.ReproduceNAT {
args.NATBlob = true
f, cleanup, err := writeNATBlob()
f, err := writeNATBlob()
if err != nil {
return fmt.Errorf("failed to write NAT blob: %v", err)
}
defer cleanup()
args.FilePayload.Files = append(args.FilePayload.Files, f)
}
+11 -14
View File
@@ -57,11 +57,11 @@ func isGSOEnabled(fd int, intf string) (bool, error) {
return val.val != 0, nil
}
func writeNATBlob() (*os.File, func(), error) {
func writeNATBlob() (*os.File, error) {
// Open a socket to use with iptables.
iptSock, err := unix.Socket(unix.AF_INET, unix.SOCK_RAW, unix.IPPROTO_ICMP)
if err != nil {
return nil, nil, fmt.Errorf("failed to open socket for iptables: %v", err)
return nil, fmt.Errorf("failed to open socket for iptables: %v", err)
}
defer unix.Close(iptSock)
@@ -78,7 +78,7 @@ func writeNATBlob() (*os.File, func(), error) {
uintptr(unsafe.Pointer(&natInfoLen)),
0)
if errno != 0 {
return nil, nil, fmt.Errorf("failed to call IPT_SO_GET_INFO: %v", err)
return nil, fmt.Errorf("failed to call IPT_SO_GET_INFO: %v", err)
}
// Get the iptables entries.
@@ -94,7 +94,7 @@ func writeNATBlob() (*os.File, func(), error) {
uintptr(unsafe.Pointer(&entriesBufLen)),
0)
if errno != 0 {
return nil, nil, fmt.Errorf("failed to call IPT_SO_GET_ENTRIES: %v", errno)
return nil, fmt.Errorf("failed to call IPT_SO_GET_ENTRIES: %v", errno)
}
var gotEntries linux.IPTGetEntries
gotEntries.UnmarshalUnsafe(entriesBuf[:unsafe.Sizeof(entries)])
@@ -119,17 +119,14 @@ func writeNATBlob() (*os.File, func(), error) {
panic(fmt.Sprintf("failed to populate entry table: copied %d bytes, but wanted to copy %d", n, natInfo.Size))
}
// Write blob to file.
blobFile, err := os.CreateTemp("", "iptables-blob-")
// Write blob to a pipe.
reader, writer, err := os.Pipe()
if err != nil {
return nil, nil, fmt.Errorf("failed to create iptables blob file: %v", err)
return nil, fmt.Errorf("failed to create iptables blob pipe: %v", err)
}
if n, err := blobFile.Write(replaceBuf); n != len(replaceBuf) || err != nil {
os.Remove(blobFile.Name())
return nil, nil, fmt.Errorf("failed to write iptables blob: wrote %d bytes (%d expected) and got error: %v", n, len(replaceBuf), err)
defer writer.Close()
if n, err := writer.Write(replaceBuf); n != len(replaceBuf) || err != nil {
return nil, fmt.Errorf("failed to write iptables blob: wrote %d bytes (%d expected) and got error: %v", n, len(replaceBuf), err)
}
cleanup := func() {
os.Remove(blobFile.Name())
}
return blobFile, cleanup, nil
return reader, nil
}