github.com/google/syzkaller@v0.0.0-20251211124644-a066d2bc4b02/prog/encoding_test.go (about)

     1  // Copyright 2016 syzkaller project authors. All rights reserved.
     2  // Use of this source code is governed by Apache 2 LICENSE that can be found in the LICENSE file.
     3  
     4  package prog
     5  
     6  import (
     7  	"bytes"
     8  	"fmt"
     9  	"math/rand"
    10  	"reflect"
    11  	"sort"
    12  	"testing"
    13  
    14  	"github.com/stretchr/testify/assert"
    15  	"github.com/stretchr/testify/require"
    16  )
    17  
    18  func setToArray(s map[string]struct{}) []string {
    19  	a := make([]string, 0, len(s))
    20  	for c := range s {
    21  		a = append(a, c)
    22  	}
    23  	sort.Strings(a)
    24  	return a
    25  }
    26  
    27  func TestSerializeData(t *testing.T) {
    28  	t.Parallel()
    29  	r := rand.New(rand.NewSource(0))
    30  	for _, readable := range []bool{false, true} {
    31  		for i := 0; i < 1e3; i++ {
    32  			data := make([]byte, r.Intn(4))
    33  			for i := range data {
    34  				data[i] = byte(r.Intn(256))
    35  			}
    36  			buf := new(bytes.Buffer)
    37  			serializeData(buf, data, readable)
    38  			p := newParser(nil, buf.Bytes(), true, false)
    39  			if !p.Scan() {
    40  				t.Fatalf("parser does not scan")
    41  			}
    42  			data1, _, err := p.deserializeData()
    43  			if err != nil {
    44  				t.Fatalf("failed to deserialize %q -> %s: %v", data, buf.Bytes(), err)
    45  			}
    46  			if !bytes.Equal(data, data1) {
    47  				t.Fatalf("corrupted data %q -> %s -> %q", data, buf.Bytes(), data1)
    48  			}
    49  		}
    50  	}
    51  }
    52  
    53  func TestCallSet(t *testing.T) {
    54  	t.Parallel()
    55  	tests := []struct {
    56  		prog   string
    57  		ok     bool
    58  		calls  []string
    59  		ncalls int
    60  	}{
    61  		{
    62  			"",
    63  			false,
    64  			[]string{},
    65  			0,
    66  		},
    67  		{
    68  			"r0 =  (foo)",
    69  			false,
    70  			[]string{},
    71  			0,
    72  		},
    73  		{
    74  			"getpid()",
    75  			true,
    76  			[]string{"getpid"},
    77  			1,
    78  		},
    79  		{
    80  			"r11 =  getpid()",
    81  			true,
    82  			[]string{"getpid"},
    83  			1,
    84  		},
    85  		{
    86  			"getpid()\n" +
    87  				"open(0x1, something that this package may not understand)\n" +
    88  				"getpid()\n" +
    89  				"#read()\n" +
    90  				"\n" +
    91  				"close$foo(&(0x0000) = {})\n",
    92  			true,
    93  			[]string{"getpid", "open", "close$foo"},
    94  			4,
    95  		},
    96  	}
    97  	for i, test := range tests {
    98  		t.Run(fmt.Sprint(i), func(t *testing.T) {
    99  			calls, ncalls, err := CallSet([]byte(test.prog))
   100  			if err != nil && test.ok {
   101  				t.Fatalf("parsing failed: %v", err)
   102  			}
   103  			if err == nil && !test.ok {
   104  				t.Fatalf("parsing did not fail")
   105  			}
   106  			callArray := setToArray(calls)
   107  			sort.Strings(test.calls)
   108  			if !reflect.DeepEqual(callArray, test.calls) {
   109  				t.Fatalf("got call set %+v, expect %+v", callArray, test.calls)
   110  			}
   111  			if ncalls != test.ncalls {
   112  				t.Fatalf("got %v calls, expect %v", ncalls, test.ncalls)
   113  			}
   114  		})
   115  	}
   116  }
   117  
   118  func TestCallSetRandom(t *testing.T) {
   119  	target, rs, iters := initTest(t)
   120  	ct := target.DefaultChoiceTable()
   121  	for i := 0; i < iters; i++ {
   122  		const ncalls = 10
   123  		p := target.Generate(rs, ncalls, ct)
   124  		calls0 := make(map[string]struct{})
   125  		for _, c := range p.Calls {
   126  			calls0[c.Meta.Name] = struct{}{}
   127  		}
   128  		calls1, ncalls1, err := CallSet(p.Serialize())
   129  		if err != nil {
   130  			t.Fatalf("CallSet failed: %v", err)
   131  		}
   132  		callArray0 := setToArray(calls0)
   133  		callArray1 := setToArray(calls1)
   134  		if !reflect.DeepEqual(callArray0, callArray1) {
   135  			t.Fatalf("got call set:\n%+v\nexpect:\n%+v", callArray1, callArray0)
   136  		}
   137  		if ncalls1 != ncalls {
   138  			t.Fatalf("got %v calls, expect %v", ncalls1, ncalls)
   139  		}
   140  	}
   141  }
   142  
   143  func TestDeserialize(t *testing.T) {
   144  	TestDeserializeHelper(t, "test", "64", nil, []DeserializeTest{
   145  		{
   146  			In:  `test$struct(&(0x7f0000000000)={0x0, {0x0}})`,
   147  			Out: `test$struct(&(0x7f0000000000))`,
   148  		},
   149  		{
   150  			In:        `test$struct(&(0x7f0000000000)=0x0)`,
   151  			Out:       `test$struct(&(0x7f0000000000))`,
   152  			StrictErr: "wrong int arg",
   153  		},
   154  		{
   155  			In:  `test$regression1(&(0x7f0000000000)=[{"000000"}, {"0000000000"}])`,
   156  			Out: `test$regression1(&(0x7f0000000000)=[{}, {}])`,
   157  		},
   158  		{
   159  			In:  `test$regression2(&(0x7f0000000000)=[0x1, 0x2, 0x3, 0x4, 0x5, 0x6])`,
   160  			Out: `test$regression2(&(0x7f0000000000)=[0x1, 0x2, 0x3, 0x4])`,
   161  		},
   162  		{
   163  			In:        `test_excessive_args1(0x0, 0x1, {0x1, &(0x7f0000000000)=[0x1, 0x2]})`,
   164  			Out:       `test_excessive_args1()`,
   165  			StrictErr: "excessive syscall arguments",
   166  		},
   167  		{
   168  			In:        `test_excessive_args2(0x0, 0x1, {0x1, &(0x7f0000000000)={0x1, 0x2}})`,
   169  			Out:       `test_excessive_args2(0x0)`,
   170  			StrictErr: "excessive syscall arguments",
   171  		},
   172  		{
   173  			In:        `test_excessive_args2(0x0, 0x1, {0x1, &(0x7f0000000000)=nil})`,
   174  			Out:       `test_excessive_args2(0x0)`,
   175  			StrictErr: "excessive syscall arguments",
   176  		},
   177  		{
   178  			In:        `test_excessive_args2(0x0, &(0x7f0000000000), 0x0)`,
   179  			Out:       `test_excessive_args2(0x0)`,
   180  			StrictErr: "excessive syscall arguments",
   181  		},
   182  		{
   183  			In:        `test$excessive_fields1(&(0x7f0000000000)={0x1, &(0x7f0000000000)=[{0x0}, 0x2]}, {0x1, 0x2, [0x1, 0x2]})`,
   184  			Out:       `test$excessive_fields1(&(0x7f0000000000)={0x1})`,
   185  			StrictErr: "excessive struct excessive_fields fields",
   186  		},
   187  		{
   188  			In: `test$excessive_fields1(0x0)`,
   189  		},
   190  		{
   191  			In:        `test$excessive_fields1(r0)`,
   192  			Out:       `test$excessive_fields1(&(0x7f0000000000))`,
   193  			StrictErr: "undeclared variable r0",
   194  		},
   195  		{
   196  			In:        `test_excessive_args2(r1)`,
   197  			Out:       `test_excessive_args2(0x0)`,
   198  			StrictErr: "undeclared variable r1",
   199  		},
   200  		{
   201  			In:        `test_excessive_args2({0x0, 0x1})`,
   202  			Out:       `test_excessive_args2(0x0)`,
   203  			StrictErr: "wrong struct arg",
   204  		},
   205  		{
   206  			In:        `test_excessive_args2([0x0], 0x0)`,
   207  			Out:       `test_excessive_args2(0x0)`,
   208  			StrictErr: "wrong array arg",
   209  		},
   210  		{
   211  			In:        `test_excessive_args2(@foo)`,
   212  			Out:       `test_excessive_args2(0x0)`,
   213  			StrictErr: "wrong union arg",
   214  		},
   215  		{
   216  			In:        `test_excessive_args2('foo')`,
   217  			Out:       `test_excessive_args2(0x0)`,
   218  			StrictErr: "wrong string arg",
   219  		},
   220  		{
   221  			In:        `test_excessive_args2(&(0x7f0000000000)={0x0, 0x1})`,
   222  			Out:       `test_excessive_args2(0x0)`,
   223  			StrictErr: "wrong addr arg",
   224  		},
   225  		{
   226  			In:  `test_excessive_args2(nil)`,
   227  			Out: `test_excessive_args2(0x0)`,
   228  		},
   229  		{
   230  			In:        `test$type_confusion1(&(0x7f0000000000)=@unknown)`,
   231  			Out:       `test$type_confusion1(&(0x7f0000000000))`,
   232  			StrictErr: `wrong option "unknown" of union "type_confusion", available options are: "f1"`,
   233  		},
   234  		{
   235  			In:        `test$type_confusion1(&(0x7f0000000000)=@unknown={0x0, 'abc'}, 0x0)`,
   236  			Out:       `test$type_confusion1(&(0x7f0000000000))`,
   237  			StrictErr: `wrong option "unknown" of union "type_confusion", available options are: "f1"`,
   238  		},
   239  		{
   240  			In:        `test$excessive_fields1(&(0x7f0000000000)=0x0)`,
   241  			Out:       `test$excessive_fields1(&(0x7f0000000000))`,
   242  			StrictErr: "wrong int arg",
   243  		},
   244  		{
   245  			In: `test$excessive_fields1(0xffffffffffffffff)`,
   246  		},
   247  		{
   248  			In: `test$excessive_fields1(0xfffffffffffffffe)`,
   249  		},
   250  		{
   251  			In:  `test$excessive_fields1(0xfffffffffffffffd)`,
   252  			Out: `test$excessive_fields1(0x0)`,
   253  		},
   254  		{
   255  			In:  `test$excessive_fields1(0xfffffffffffffffc)`,
   256  			Out: `test$excessive_fields1(0xffffffffffffffff)`,
   257  		},
   258  		{
   259  			In:  `test$auto0(AUTO, &AUTO={AUTO, AUTO, 0x1}, AUTO, 0x0)`,
   260  			Out: `test$auto0(0x42, &(0x7f0000000040)={0xc, 0x43, 0x1}, 0xc, 0x0)`,
   261  		},
   262  		{
   263  			In:  `test$auto0(AUTO, &AUTO={AUTO, AUTO, AUTO}, AUTO, 0x0)`,
   264  			Err: `wrong type *prog.IntType for AUTO`,
   265  		},
   266  		{
   267  			In:  `test$auto1(AUTO, &AUTO=AUTO, AUTO, 0x0)`,
   268  			Out: `test$auto1(0x42, &(0x7f0000000040)={0xc, 0x43, 0x0}, 0xc, 0x0)`,
   269  		},
   270  		{
   271  			In:  `test$auto2(AUTO, &AUTO=AUTO, AUTO, 0x0)`,
   272  			Out: `test$auto2(0x42, &(0x7f0000000040)={0x10, {0xc, 0x43, 0x0}}, 0x10, 0x0)`,
   273  		},
   274  		{
   275  			In:  `test$auto0(AUTO, &AUTO=AUTO, AUTO, 0x0)`,
   276  			Err: `wrong type *prog.IntType for AUTO`,
   277  		},
   278  		{
   279  			In:  `test$bf2(&AUTO={AUTO, 0x10, 0x0, AUTO})`,
   280  			Out: `test$bf2(&(0x7f0000000040)={0x8, 0x10, 0x0, 0x18})`,
   281  		},
   282  		{
   283  			In:  `test$str0(&AUTO="303100090a0d7022273a")`,
   284  			Out: `test$str0(&(0x7f0000000040)='01\x00\t\n\rp\"\':')`,
   285  		},
   286  		{
   287  			In:  `test$blob0(&AUTO="303100090a0d7022273a")`,
   288  			Out: `test$blob0(&(0x7f0000000040)='01\x00\t\n\rp\"\':')`,
   289  		},
   290  		{
   291  			In:  `test$blob0(&AUTO="3031000a0d7022273a01")`,
   292  			Out: `test$blob0(&(0x7f0000000040)="3031000a0d7022273a01")`,
   293  		},
   294  		{
   295  			In:        `test$out_const(&(0x7f0000000000)=0x2)`,
   296  			Out:       `test$out_const(&(0x7f0000000000))`,
   297  			StrictErr: `out arg const[1, const] has non-default value: 2`,
   298  		},
   299  		{
   300  			In:  `test$str1(&(0x7f0000000000)='foo\x00')`,
   301  			Out: `test$str1(&(0x7f0000000000))`,
   302  		},
   303  		{
   304  			In:        `test$str1(&(0x7f0000000000)='bar\x00')`,
   305  			Out:       `test$str1(&(0x7f0000000000))`,
   306  			StrictErr: `bad string value "bar\x00", expect ["foo\x00"]`,
   307  		},
   308  		{
   309  			In: `test$str2(&(0x7f0000000000)='bar\x00')`,
   310  		},
   311  		{
   312  			In:        `test$str2(&(0x7f0000000000)='baz\x00')`,
   313  			Out:       `test$str2(&(0x7f0000000000)='foo\x00')`,
   314  			StrictErr: `bad string value "baz\x00", expect ["foo\x00" "bar\x00"]`,
   315  		},
   316  		{
   317  			In:  `test$opt2(&(0x7f0000000000))`,
   318  			Out: `test$opt2(0x0)`,
   319  		},
   320  		{
   321  			In:        `test$opt2(&(0x7f0000000001))`,
   322  			Out:       `test$opt2(0x0)`,
   323  			StrictErr: `unaligned vma address 0x1`,
   324  		},
   325  		{
   326  			In:  `test$opt2(&(0x7f0000000000)=nil)`,
   327  			Out: `test$opt2(0x0)`,
   328  		},
   329  		{
   330  			In:        `test$opt2(&(0x7f0000000000)='foo')`,
   331  			Out:       `test$opt2(0x0)`,
   332  			StrictErr: `non-nil argument for nil type`,
   333  		},
   334  		{
   335  			In:        `test$opt2(0x0) (non_existing_prop: 123)`,
   336  			Out:       `test$opt2(0x0)`,
   337  			StrictErr: `unknown call property: non_existing_prop`,
   338  		},
   339  		{
   340  			In:        `test$opt2(0x0) (fail_nth: zzz)`,
   341  			Out:       `test$opt2(0x0)`,
   342  			StrictErr: `invalid int value: zzz`,
   343  		},
   344  		{
   345  			In:        `test$opt2(0x0) (non_existing_prop: 123, fail_nth: 1)`,
   346  			Out:       `test$opt2(0x0) (fail_nth: 1)`,
   347  			StrictErr: `unknown call property: non_existing_prop`,
   348  		},
   349  		{
   350  			In:  `test$opt2(0x0) (fail_nth: 0)`,
   351  			Out: `test$opt2(0x0)`,
   352  		},
   353  		{
   354  			In:  `test$str2(&(0x7f0000000000)="$eJwqrqzKTszJSS0CBAAA//8TyQPi`,
   355  			Err: `want ", got EOF`,
   356  		},
   357  		{
   358  			In: `mutate9(&(0x7f0000000000)='./local/filename\x00')`,
   359  		},
   360  		{
   361  			In:  `mutate9(&(0x7f0000000000)='/escaping/filename\x00')`,
   362  			Err: `escaping filename`,
   363  		},
   364  	})
   365  }
   366  
   367  func TestSerializeDeserialize(t *testing.T) {
   368  	TestDeserializeHelper(t, "test", "64", nil, []DeserializeTest{
   369  		{
   370  			In:  `serialize0(&(0x7f0000408000)={"6861736800000000000000000000", "48490000"})`,
   371  			Out: `serialize0(&(0x7f0000408000)={'hash\x00', 'HI\x00'})`,
   372  		},
   373  		{
   374  			In:  `serialize1(&(0x7f0000000000)="0000000000000000", 0x8)`,
   375  			Out: `serialize1(&(0x7f0000000000)=""/8, 0x8)`,
   376  		},
   377  		{
   378  			In:  `serialize2(&(0x7f0000000000)="$c3l6a2FsbGVy")`,
   379  			Out: `serialize2(&(0x7f0000000000)='syzkaller')`,
   380  		},
   381  		{
   382  			In: `serialize3(&(0x7f0000000000)="$eJwqrqzKTszJSS0CBAAA//8TyQPi")`,
   383  		},
   384  		{
   385  			In:        `foo$any_filename(&(0x7f0000000000)=ANY=[@ANYBLOB='/'])`,
   386  			Out:       `foo$any_filename(&(0x7f0000000000)=@complex={0x0, 0x0, 0x0, 0x0, {0x0, 0x0, 0x0, 0x0, 0x0, 0x0}, []})`,
   387  			StrictErr: `wrong array arg`,
   388  		},
   389  	})
   390  }
   391  
   392  func TestDeserializeDataMmapProg(t *testing.T) {
   393  	testEachTarget(t, func(t *testing.T, target *Target) {
   394  		p := target.DataMmapProg()
   395  		data := p.Serialize()
   396  		p2, err := target.Deserialize(data, StrictUnsafe)
   397  		assert.NoError(t, err)
   398  		data2 := p2.Serialize()
   399  		assert.Equal(t, string(data), string(data2))
   400  		p.SerializeForExec()
   401  	})
   402  }
   403  
   404  func TestSerializeDeserializeRandom(t *testing.T) {
   405  	testEachTargetRandom(t, func(t *testing.T, target *Target, rs rand.Source, iters int) {
   406  		ct := target.DefaultChoiceTable()
   407  		for i := 0; i < iters; i++ {
   408  			p0 := target.Generate(rs, 10, ct)
   409  			if _, _, ok := testSerializeDeserialize(t, p0); ok {
   410  				continue
   411  			}
   412  			p0, _ = Minimize(p0, -1, MinimizeCorpus, func(p1 *Prog, _ int) bool {
   413  				_, _, ok := testSerializeDeserialize(t, p1)
   414  				return !ok
   415  			})
   416  			data0, data1, ok := testSerializeDeserialize(t, p0)
   417  			if ok {
   418  				t.Log("flaky?")
   419  			}
   420  			decoded0, err := target.DeserializeExec(data0, nil)
   421  			if err != nil {
   422  				t.Fatal(err)
   423  			}
   424  			decoded1, err := target.DeserializeExec(data1, nil)
   425  			if err != nil {
   426  				t.Fatal(err)
   427  			}
   428  			t.Logf("decoded0: %+v", decoded0)
   429  			t.Logf("decoded1: %+v", decoded1)
   430  			t.Fatalf("was: %q\ngot: %q\nprogram:\n%s", data0, data1, p0.Serialize())
   431  		}
   432  	})
   433  }
   434  
   435  func testSerializeDeserialize(t *testing.T, p0 *Prog) ([]byte, []byte, bool) {
   436  	data0, err := p0.SerializeForExec()
   437  	if err != nil {
   438  		t.Fatal(err)
   439  	}
   440  	serialized := p0.Serialize()
   441  	p1, err := p0.Target.Deserialize(serialized, NonStrict)
   442  	if err != nil {
   443  		t.Fatal(err)
   444  	}
   445  	data1, err := p1.SerializeForExec()
   446  	if err != nil {
   447  		t.Fatal(err)
   448  	}
   449  	if !bytes.Equal(data0, data1) {
   450  		t.Logf("PROG0:\n%s", p0.Serialize())
   451  		t.Logf("PROG1:\n%s", p1.Serialize())
   452  		return data0, data1, false
   453  	}
   454  	return nil, nil, true
   455  }
   456  
   457  func TestSerializeCallProps(t *testing.T) {
   458  	target := initTargetTest(t, "test", "64")
   459  	type SerializeCallPropsTest struct {
   460  		prog  string
   461  		props []CallProps
   462  	}
   463  
   464  	tests := []SerializeCallPropsTest{
   465  		{
   466  			"serialize0(0x0)\n",
   467  			[]CallProps{{}},
   468  		},
   469  		{
   470  			"serialize0(0x0) ()\n",
   471  			[]CallProps{{}},
   472  		},
   473  		{
   474  			"serialize0(0x0) (fail_nth: 5)\n",
   475  			[]CallProps{{5, false, 0}},
   476  		},
   477  		{
   478  			"serialize0(0x0) (fail_nth)\n",
   479  			nil,
   480  		},
   481  		{
   482  			"serialize0(0x0) (fail_nth: \"5\")\n",
   483  			nil,
   484  		},
   485  		{
   486  			"serialize0(0x0) (async)\n",
   487  			[]CallProps{{0, true, 0}},
   488  		},
   489  		{
   490  			"serialize0(0x0) (async, rerun: 10)\n",
   491  			[]CallProps{{0, true, 10}},
   492  		},
   493  	}
   494  
   495  	for _, test := range tests {
   496  		p, err := target.Deserialize([]byte(test.prog), Strict)
   497  		if test.props != nil && err != nil {
   498  			t.Fatal(err)
   499  		} else if test.props == nil && err == nil {
   500  			t.Errorf("expected an error, but got none\n%s", test.prog)
   501  		}
   502  
   503  		for i, props := range test.props {
   504  			if !reflect.DeepEqual(props, p.Calls[i].Props) {
   505  				t.Errorf("%v-th call props differ: %v != %v", i, props, p.Calls[i].Props)
   506  			}
   507  		}
   508  	}
   509  }
   510  
   511  func TestDeserializeComments(t *testing.T) {
   512  	target := initTargetTest(t, "test", "64")
   513  	p, err := target.Deserialize([]byte(`
   514  # comment1
   515  # comment2
   516  serialize0(0x0)
   517  serialize0(0x0)
   518  # comment3
   519  serialize0(0x0)
   520  # comment4
   521  serialize0(0x0)	#  comment5
   522  #comment6
   523  
   524  serialize0(0x0)
   525  #comment7
   526  `), Strict)
   527  	if err != nil {
   528  		t.Fatal(err)
   529  	}
   530  	for i, want := range []string{
   531  		"comment2",
   532  		"",
   533  		"comment3",
   534  		"comment5",
   535  		"",
   536  	} {
   537  		if got := p.Calls[i].Comment; got != want {
   538  			t.Errorf("bad call %v comment: %q, want %q", i, got, want)
   539  		}
   540  	}
   541  	wantComments := []string{
   542  		"comment1",
   543  		"comment4",
   544  		"comment6",
   545  		"comment7",
   546  	}
   547  	if !reflect.DeepEqual(p.Comments, wantComments) {
   548  		t.Errorf("bad program comments %q\nwant: %q", p.Comments, wantComments)
   549  	}
   550  }
   551  
   552  func TestHasNext(t *testing.T) {
   553  	testCases := []struct {
   554  		input    string
   555  		expected bool
   556  	}{
   557  		{"abcdef", true},
   558  		{"xyz", false},
   559  		{"ab", false},
   560  		{"abc", true},
   561  	}
   562  	for _, testCase := range testCases {
   563  		p := newParser(nil, []byte(testCase.input), true, false)
   564  		if !p.Scan() {
   565  			t.Fatalf("parser does not scan")
   566  		}
   567  		result := p.HasNext("abc")
   568  		if result != testCase.expected {
   569  			t.Errorf("expected HasNext(\"abc\") on input %q to be %v, but got %v",
   570  				testCase.input, testCase.expected, result)
   571  		}
   572  	}
   573  }
   574  
   575  // nolint: lll
   576  func TestDeserializeSkipImage(t *testing.T) {
   577  	target := initTargetTest(t, "linux", "amd64")
   578  	p, err := target.Deserialize([]byte(`
   579  syz_mount_image$ext4(&(0x7f0000000080)='ext4\x00', &(0x7f00000000c0)='./file0\x00', 0x0, &(0x7f0000000100), 0x1, 0x71, &(0x7f0000000140)="$eJzszrENAVAUBdDrLyASnUIYwA5GESWdiljJDiYwgg0UWs1XfArfABI5J3kvue827/I4Tc6zpA6T2tntD5vVtu3wl0qSUZJxkum85duydYNXf70f1+/59b8AAAAAAAAAwLeSRZ8/Ds8AAAD//9ZiI98=")
   580  `), Strict)
   581  	require.NoError(t, err)
   582  	assert.Equal(t, `syz_mount_image$ext4(&(0x7f0000000080)='ext4\x00', &(0x7f00000000c0)='./file0\x00', 0x0, &(0x7f0000000100), 0x1, 0x71, &(0x7f0000000140)="<<IMAGE>>")
   583  `,
   584  		string(p.Serialize(SkipImages)))
   585  }