[vm] Fix incorrect socket/unix-domain-socket binding code for shared sockets

When creating a binding socket with `shared: true` there will be one
underlying [OSSocket] used. Any following bind on the same address with
`shared: true` will re-use that [OSSocket].

The code that was searching for existing sockets is correct, but the
code that increments the refcount, ... was incorrectly using the start
of the linked list instead of the found existing socket instance.

Fixes https://github.com/dart-lang/sdk/issues/46634

TEST=standalone{,_2}/io/unix_socket_regress_46634_test

Change-Id: I3ce1bdc98ecd4b5311f826ab2597a62fe048be09
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/207083
Reviewed-by: Alexander Aprelev <aam@google.com>
Commit-Queue: Martin Kustermann <kustermann@google.com>
diff --git a/runtime/bin/socket.cc b/runtime/bin/socket.cc
index ec52dad..1f39427c 100644
--- a/runtime/bin/socket.cc
+++ b/runtime/bin/socket.cc
@@ -130,13 +130,13 @@
         // created the socket. Feed same fd and store it into native field
         // of dart socket_object. Sockets here will share same fd but contain a
         // different port() through EventHandler_SendData.
-        Socket* socketfd = new Socket(os_socket->fd);
-        os_socket->ref_count++;
+        Socket* socketfd = new Socket(os_socket_same_addr->fd);
+        os_socket_same_addr->ref_count++;
         // We set as a side-effect the file descriptor on the dart
         // socket_object.
         Socket::ReuseSocketIdNativeField(socket_object, socketfd,
                                          Socket::kFinalizerListening);
-        InsertByFd(socketfd, os_socket);
+        InsertByFd(socketfd, os_socket_same_addr);
         return Dart_True();
       }
     }
@@ -234,13 +234,13 @@
         // created the socket. Feed the same fd and store it into the native
         // field of dart socket_object. Sockets here will share same fd but
         // contain a different port() through EventHandler_SendData.
-        Socket* socketfd = new Socket(os_socket->fd);
-        os_socket->ref_count++;
+        Socket* socketfd = new Socket(os_socket_same_addr->fd);
+        os_socket_same_addr->ref_count++;
         // We set as a side-effect the file descriptor on the dart
         // socket_object.
         Socket::ReuseSocketIdNativeField(socket_object, socketfd,
                                          Socket::kFinalizerListening);
-        InsertByFd(socketfd, os_socket);
+        InsertByFd(socketfd, os_socket_same_addr);
         return Dart_True();
       }
     }
diff --git a/tests/standalone/io/unix_socket_regress_46634_test.dart b/tests/standalone/io/unix_socket_regress_46634_test.dart
new file mode 100644
index 0000000..31bce79
--- /dev/null
+++ b/tests/standalone/io/unix_socket_regress_46634_test.dart
@@ -0,0 +1,20 @@
+// Copyright (c) 2021, the Dart project authors.  Please see the AUTHORS file
+// for details. All rights reserved. Use of this source code is governed by a
+// BSD-style license that can be found in the LICENSE file.
+
+import 'dart:io';
+
+import 'unix_socket_test.dart' show withTempDir, testListenCloseListenClose;
+
+void main() async {
+  if (!Platform.isMacOS && !Platform.isLinux && !Platform.isAndroid) {
+    return;
+  }
+  final futures = <Future>[];
+  for (int i = 0; i < 10; ++i) {
+    futures.add(withTempDir('unix_socket_test', (Directory dir) async {
+      await testListenCloseListenClose('${dir.path}');
+    }));
+  }
+  await Future.wait(futures);
+}
diff --git a/tests/standalone/io/unix_socket_test.dart b/tests/standalone/io/unix_socket_test.dart
index 0553e6a..195406c 100644
--- a/tests/standalone/io/unix_socket_test.dart
+++ b/tests/standalone/io/unix_socket_test.dart
@@ -3,8 +3,8 @@
 // BSD-style license that can be found in the LICENSE file.
 
 import 'dart:async';
-import 'dart:io';
 import 'dart:convert';
+import 'dart:io';
 
 import 'package:expect/expect.dart';
 
diff --git a/tests/standalone_2/io/unix_socket_regress_46634_test.dart b/tests/standalone_2/io/unix_socket_regress_46634_test.dart
new file mode 100644
index 0000000..8920965
--- /dev/null
+++ b/tests/standalone_2/io/unix_socket_regress_46634_test.dart
@@ -0,0 +1,21 @@
+// Copyright (c) 2021, the Dart project authors.  Please see the AUTHORS file
+// for details. All rights reserved. Use of this source code is governed by a
+// BSD-style license that can be found in the LICENSE file.
+
+// @dart = 2.9
+import 'dart:io';
+
+import 'unix_socket_test.dart' show withTempDir, testListenCloseListenClose;
+
+void main() async {
+  if (!Platform.isMacOS && !Platform.isLinux && !Platform.isAndroid) {
+    return;
+  }
+  final futures = <Future>[];
+  for (int i = 0; i < 10; ++i) {
+    futures.add(withTempDir('unix_socket_test', (Directory dir) async {
+      await testListenCloseListenClose('${dir.path}');
+    }));
+  }
+  await Future.wait(futures);
+}