質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.48%
C#

C#はマルチパラダイムプログラミング言語の1つで、命令形・宣言型・関数型・ジェネリック型・コンポーネント指向・オブジェクティブ指向のプログラミング開発すべてに対応しています。

Visual Studio

Microsoft Visual StudioはMicrosoftによる統合開発環境(IDE)です。多種多様なプログラミング言語に対応しています。

Windows

Windowsは、マイクロソフト社が開発したオペレーティングシステムです。当初は、MS-DOSに変わるOSとして開発されました。 GUIを採用し、主にインテル系のCPUを搭載したコンピューターで動作します。Windows系OSのシェアは、90%を超えるといわれています。 パソコン用以外に、POSシステムやスマートフォンなどの携帯端末用、サーバ用のOSもあります。

Win32 API

Win32 APIはMicrosoft Windowsの32bitプロセッサのOSで動作するAPIです。

Q&A

解決済

2回答

27001閲覧

C#でのソケット通信 ソケットの再利用がしたい

nc163

総合スコア12

C#

C#はマルチパラダイムプログラミング言語の1つで、命令形・宣言型・関数型・ジェネリック型・コンポーネント指向・オブジェクティブ指向のプログラミング開発すべてに対応しています。

Visual Studio

Microsoft Visual StudioはMicrosoftによる統合開発環境(IDE)です。多種多様なプログラミング言語に対応しています。

Windows

Windowsは、マイクロソフト社が開発したオペレーティングシステムです。当初は、MS-DOSに変わるOSとして開発されました。 GUIを採用し、主にインテル系のCPUを搭載したコンピューターで動作します。Windows系OSのシェアは、90%を超えるといわれています。 パソコン用以外に、POSシステムやスマートフォンなどの携帯端末用、サーバ用のOSもあります。

Win32 API

Win32 APIはMicrosoft Windowsの32bitプロセッサのOSで動作するAPIです。

0グッド

1クリップ

投稿2017/06/02 21:48

編集2017/06/02 21:50

C#でソケット通信のプログラムを書いていて、解決できない問題があるので質問させてください
やりたいこと、System.Net.Sockets.Socket を再利用したいです。
以下のプログラムのようなことを例外なく実行させるには、何が足り何のでしょうか?
新しいインスタンスを作ることなく実行したいです

###発生している問題・エラーメッセージ
System.InvalidOperationException: 'ソケットがいったん切断されると、非同期、および異なる EndPoint でのみ再び受け取ることができます。 操作が完了するまで終了しないスレッド上で BeginConnect を呼び出さなければなりません。'

###該当のソースコード
class Class1
{
Socket socket;
public Class1()
{
socket = new Socket(AddressFamily.InterNetwork,SocketType.Stream,ProtocolType.Tcp);

var remoteIpEp = new IPEndPoint(IPAddress.Parse("127.0.0.1"), 54321); socket.Connect(remoteIpEp ); socket.Disconnect(true); socket.Connect(remoteIpEp ); //ここで例外 socket.Disconnect(true); }

}

###試したこと
・socket.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.ReuseAddress, true);
・socket.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.DontLinger, true);
・socket.BeginConnectなど利用しても同じ例外にはまってしまいました。
・socket.Shutdown(SocketShutdown.Both);

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

Zuishin

2017/06/04 13:19

そもそもなぜ切断・接続を繰り返しながらソケットを再利用しなければならないのですか?
nc163

2017/06/04 15:43

すいません、特にありません TCPクライアントクラスをお試しで作って一通り機能を揃えようしたところ躓いていました 
guest

回答2

0

ベストアンサー

僕の理解では出来ません。

DisconnectしたらWindowsの仕様で数十秒間は同じポートは使えません。

一応ぐぐってみました。
下記の回答のベストアンサーが詳しいです。
https://stackoverflow.com/questions/27182180/how-to-reconnect-to-a-socket-gracefully

Windowsは即座に同じポートを再利用できません。
頻繁にデータを送ったり受け取ったりするならソケットは生かしっぱなしにしておけばいいです。

先の回答にDisconnect後には最低30秒、最長240秒は必要とあります。
この間をConnectメソッドは待つことができません。
MSDNのSocketのConnectメソッドの説明にもこれを待ちたければ非同期バージョンのBeginConnectを使えとあります。
例外情報とも一致しています。
メソッドの仕様を参照してください。(日本語訳は壊滅的ですが)

ただ、仕様を見直した方がいいと思います。

投稿2017/06/04 03:34

haru666

総合スコア1591

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

nc163

2017/06/04 04:33

ありがとうございます BeginConnecを使用しても即座に例外に入ってしまいましたが、、、思えば自分もその仕様の聞き覚えがありました 調べてみます 情報ありがとうございます
hsk

2017/06/07 02:53 編集

もう解決されたかもしれませんが、.NET Framework 4.5.2のソース (http://referencesource.microsoft.com/ DOWNLOAD可) をみると、System.Net.Sockets.Socket クラスは private bool m_IsDisconnected; フィールドをもっていて、(同期式の)Disconnect メソッドでは SetToDisconnect 内部メソッドを介して m_IsDisconnected = true; としていて、Connect メソッドでは、いわゆるガード節で if(m_IsDisconnected){ throw new InvalidOperationException(SR.GetString(SR.net_sockets_disconnectedConnect)); と書かれていることがわかります。m_IsDisconnected = false; と戻す箇所は、SetToConnected 内部メソッドのみです。SetToConnected メソッドを呼び出すコードは、読み解いた感じでは非同期のConnect、Accept系関連内(コールバック含む)のみでした。同期式のConnect,Disconnect,再Connect ができない直接的な理由は、まさしくコードがそのように書かれているからなのですが、詳細はご自身で.NET Framework のソースコードをお調べなさるとよいかなと思います。
guest

0

投稿2017/06/03 02:45

hihijiji

総合スコア4150

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

nc163

2017/06/03 09:06

ありがとうございます これしてもダメでした 今思ったのですが、もしかしてdisconnect後に待ち時間が必要だったりするのでしょうか 後ほどその辺り含めて再度試してみようと思います
hihijiji

2017/06/03 09:11

通信相手の状態を確認するか、それが無理ならFiddler 等を使ってパケットを追ってみてください。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.48%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問