diff options
Diffstat (limited to 'pkg')
-rw-r--r-- | pkg/gate/gate_test.go | 3 | ||||
-rw-r--r-- | pkg/sentry/arch/arch_aarch64.go | 4 | ||||
-rw-r--r-- | pkg/sentry/arch/syscalls_arm64.go | 10 | ||||
-rw-r--r-- | pkg/sentry/kernel/fd_table.go | 2 | ||||
-rw-r--r-- | pkg/tcpip/transport/tcp/segment.go | 6 | ||||
-rw-r--r-- | pkg/tcpip/transport/tcp/snd.go | 3 |
6 files changed, 22 insertions, 6 deletions
diff --git a/pkg/gate/gate_test.go b/pkg/gate/gate_test.go index 850693df8..316015e06 100644 --- a/pkg/gate/gate_test.go +++ b/pkg/gate/gate_test.go @@ -15,6 +15,7 @@ package gate_test import ( + "runtime" "testing" "time" @@ -165,6 +166,8 @@ func worker(g *gate.Gate, done *sync.WaitGroup) { if !g.Enter() { break } + // Golang before v1.14 doesn't preempt busyloops. + runtime.Gosched() g.Leave() } done.Done() diff --git a/pkg/sentry/arch/arch_aarch64.go b/pkg/sentry/arch/arch_aarch64.go index b998f84fc..c29e1b841 100644 --- a/pkg/sentry/arch/arch_aarch64.go +++ b/pkg/sentry/arch/arch_aarch64.go @@ -100,6 +100,9 @@ type State struct { // FeatureSet is a pointer to the currently active feature set. FeatureSet *cpuid.FeatureSet + + // OrigR0 stores the value of register R0. + OrigR0 uint64 } // Proto returns a protobuf representation of the system registers in State. @@ -150,6 +153,7 @@ func (s *State) Fork() State { aarch64FPState: s.aarch64FPState.fork(), TPValue: s.TPValue, FeatureSet: s.FeatureSet, + OrigR0: s.OrigR0, } } diff --git a/pkg/sentry/arch/syscalls_arm64.go b/pkg/sentry/arch/syscalls_arm64.go index 00d5ef461..dc13b6124 100644 --- a/pkg/sentry/arch/syscalls_arm64.go +++ b/pkg/sentry/arch/syscalls_arm64.go @@ -50,13 +50,21 @@ func (c *context64) SyscallArgs() SyscallArguments { } // RestartSyscall implements Context.RestartSyscall. +// Prepare for system call restart, OrigR0 will be restored to R0. +// Please see the linux code as reference: +// arch/arm64/kernel/signal.c:do_signal() func (c *context64) RestartSyscall() { c.Regs.Pc -= SyscallWidth - c.Regs.Regs[8] = uint64(restartSyscallNr) + // R0 will be backed up into OrigR0 when entering doSyscall(). + // Please see the linux code as reference: + // arch/arm64/kernel/syscall.c:el0_svc_common(). + // Here we restore it back. + c.Regs.Regs[0] = uint64(c.OrigR0) } // RestartSyscallWithRestartBlock implements Context.RestartSyscallWithRestartBlock. func (c *context64) RestartSyscallWithRestartBlock() { c.Regs.Pc -= SyscallWidth + c.Regs.Regs[0] = uint64(c.OrigR0) c.Regs.Regs[8] = uint64(restartSyscallNr) } diff --git a/pkg/sentry/kernel/fd_table.go b/pkg/sentry/kernel/fd_table.go index dddc28d5a..d09d97825 100644 --- a/pkg/sentry/kernel/fd_table.go +++ b/pkg/sentry/kernel/fd_table.go @@ -338,7 +338,7 @@ func (f *FDTable) NewFDVFS2(ctx context.Context, minfd int32, file *vfs.FileDesc fd = f.next } for fd < end { - if d, _, _ := f.get(fd); d == nil { + if d, _, _ := f.getVFS2(fd); d == nil { f.setVFS2(fd, file, flags) if fd == f.next { // Update next search start position. diff --git a/pkg/tcpip/transport/tcp/segment.go b/pkg/tcpip/transport/tcp/segment.go index 1c10da5ca..5d0bc4f72 100644 --- a/pkg/tcpip/transport/tcp/segment.go +++ b/pkg/tcpip/transport/tcp/segment.go @@ -56,9 +56,9 @@ type segment struct { options []byte `state:".([]byte)"` hasNewSACKInfo bool rcvdTime time.Time `state:".(unixTime)"` - // xmitTime is the last transmit time of this segment. A zero value - // indicates that the segment has yet to be transmitted. - xmitTime time.Time `state:".(unixTime)"` + // xmitTime is the last transmit time of this segment. + xmitTime time.Time `state:".(unixTime)"` + xmitCount uint32 } func newSegment(r *stack.Route, id stack.TransportEndpointID, pkt tcpip.PacketBuffer) *segment { diff --git a/pkg/tcpip/transport/tcp/snd.go b/pkg/tcpip/transport/tcp/snd.go index b74b61e7d..657c3146e 100644 --- a/pkg/tcpip/transport/tcp/snd.go +++ b/pkg/tcpip/transport/tcp/snd.go @@ -1229,7 +1229,7 @@ func (s *sender) handleRcvdSegment(seg *segment) { // sendSegment sends the specified segment. func (s *sender) sendSegment(seg *segment) *tcpip.Error { - if !seg.xmitTime.IsZero() { + if seg.xmitCount > 0 { s.ep.stack.Stats().TCP.Retransmits.Increment() s.ep.stats.SendErrors.Retransmits.Increment() if s.sndCwnd < s.sndSsthresh { @@ -1237,6 +1237,7 @@ func (s *sender) sendSegment(seg *segment) *tcpip.Error { } } seg.xmitTime = time.Now() + seg.xmitCount++ return s.sendSegmentFromView(seg.data, seg.flags, seg.sequenceNumber) } |