天天加油 - 助您成才
Winsock完成端口模型-Delphi代码
您正在看的DELPHI是:Winsock完成端口模型-Delphi代码。

原文出处 《Windows网络编程技术》第8章 完成端口模型

由于原书附的是C代码,我把其翻译成Delphi代码。

 

其中winsock2.pas在delphi中不带,要另外下载http://jungla.dit.upm.es/~bti/files/winsock2.pas

 

 

program CompletionIO;

{$APPTYPE CONSOLE}

uses
  SysUtils,
  WinSock2 in 'WinSock2.pas',
  Mains in 'Mains.pas';

begin
    main();
end.

 

 

// Module Name: iocmplt.cpp
//
// Description:
//
//    This sample illustrates how to develop a simple echo server Winsock
//    application using the completeion port I/O model. This
//    sample is implemented as a console-style application and simply prints
//    messages when connections are established and removed from the server.
//    The application listens for TCP connections on port 5150 and accepts them
//    as they arrive. When this application receives data from a client, it
//    simply echos (this is why we call it an echo server) the data back in
//    it's original form until the client closes the connection.
//
//  2005-2-5
//    cpp convert to delphi pas  by johnson
//   

unit Mains;

interface

uses Windows, WinSock2, WinSock, Sysutils;

const
 PORT         = 5150;
 DATA_BUFSIZE = 8192;


type
  LPVOID = Pointer;
  LPPER_IO_OPERATION_DATA = ^ PER_IO_OPERATION_DATA ;
  PER_IO_OPERATION_DATA = packed record
    Overlapped: OVERLAPPED;
    DataBuf: TWSABUF;
    Buffer: array [0..DATA_BUFSIZE] of CHAR;
    BytesSEND: Dword;
    BytesRECV: Dword;
  end;

  LPPER_HANDLE_DATA = ^ PER_HANDLE_DATA;
  PER_HANDLE_DATA = packed record
    Socket: TSocket;
  end;

  procedure main;

implementation

function ServerWorkerThread(CompletionPortID: LPVOID): Dword; stdcall; forward;

procedure printf(Fmt: string; num: Integer);
begin
  WriteLn(Format(Fmt, [num]));
end;

procedure main;
var
  InternetAddr: SOCKADDR_IN;
  Listen: TSOCKET;
  Accept: TSOCKET;
  CompletionPort: THANDLE ;
  SystemInfo: SYSTEM_INFO ;
  PerHandleData: LPPER_HANDLE_DATA ;
  PerIoData: LPPER_IO_OPERATION_DATA ;
  i: Integer;
  RecVBytes:  Dword;
  Flags: Dword;
  ThreadID: Dword ;
  wsaData: TWSADATA ;
  Ret: Dword ;

  ThreadHandle: THANDLE;
begin
    Ret := WSAStartup($0202, wsaData);
    if (Ret <> 0) then
    begin
      printf('WSAStartup failed with error %d', Ret);
      Exit;
    end;

   // Setup an I/O completion port.
   CompletionPort := CreateIoCompletionPort(INVALID_HANDLE_VALUE, 0, 0, 0);
   if (CompletionPort = 0) then
   begin
      printf( 'CreateIoCompletionPort failed with error: %d', GetLastError());
      Exit;
   end;


   // Determine how many processors are on the system.

   GetSystemInfo(SystemInfo);

   // Create worker threads based on the number of processors available on the
   // system. Create two worker threads for each processor.

   for i:= 0 to SystemInfo.dwNumberOfProcessors * 2 - 1 do
   begin

      // Create a server worker thread and pass the completion port to the thread.
      ThreadHandle := CreateThread(nil, 0, @ServerWorkerThread, Pointer(CompletionPort),
         0, ThreadID);
      if (ThreadHandle = 0) then
      begin
         printf('CreateThread() failed with error %d', GetLastError());
         Exit;
      end;

      // Close the thread handle
      CloseHandle(ThreadHandle);
   end;

   // Create a listening socket
   Listen := WSASocket(AF_INET, SOCK_STREAM, 0, nil, 0, WSA_FLAG_OVERLAPPED);
   if (Listen = INVALID_SOCKET) then
   begin
      printf('WSASocket() failed with error %d', WSAGetLastError());
      exit;
   end;

   InternetAddr.sin_family := AF_INET;
   InternetAddr.sin_addr.s_addr := htonl(INADDR_ANY);
   InternetAddr.sin_port := htons(PORT);

   if (bind(Listen, InternetAddr, sizeof(InternetAddr)) = SOCKET_ERROR) then
   begin
      printf('bind() failed with error %d', WSAGetLastError());
      exit;
   end;

   // Prepare socket for listening

 

   if (Winsock.listen(Listen, 5) = SOCKET_ERROR) then
   begin
      printf('listen() failed with error %d', WSAGetLastError());
      exit;
   end
   else
   begin
      printf('Server listen on port = %d ...', PORT);
   end;


   // Accept connections and assign to the completion port.
   while(TRUE) do
   begin
      Accept := WSAAccept(Listen, nil, nil, nil, 0);
      if (Accept = SOCKET_ERROR) then
     begin
        printf('WSAAccept() failed with error %d', WSAGetLastError());
        exit;
     end;

      // Create a socket in

1 2 3 下一页

排行

  1. VB.NET中的组件开发
  2. 用vb编一个计算器,需要用到数组
  3. VB.Net的ByVal和ByRef --ByVal时
  4. VB.NET操作SQL Server完全模块
  5. VB中定制DllRegisterServer、Dll
  6. VB中打印ACCESS报表
  7. ECLIPSE ANT INTEGRATION
  8. 在eclipse + MyEclipse下配置建立
  9. 基于WebGIS的GPS系统的设计与实现
  10. JBuilder2005+JBOSS+Oracle9i开发
  11. mysql4.1.10的JDBC驱动(mysql-co
  12. 在Win2003+Tomcat+MySQL下运行JP
  13. (原创)当server碰到server,soc
  14. JavaBeans 程序开发从入门到精通
  15. [自创]JCreator安装学习使用方法
  16. Java 正则表达式自义bean
  1. 在C#中编写多线程应用程序,简单
  2. VB实现局域网内的文件传输
  3. VB.NET中的组件开发
  4. 用vb编一个计算器,需要用到数组
  5. 如何用VB.Net创建一个三层的数据
  6. VB.Net的ByVal和ByRef --ByVal时
  7. VB.NET的阳历与农历转换的算法
  8. VB.NET操作SQL Server完全模块
  9. VB中定制DllRegisterServer、Dll
  10. VB中打印ACCESS报表
  11. ECLIPSE ANT INTEGRATION
  12. 在eclipse + MyEclipse下配置建立
  13. 基于WebGIS的GPS系统的设计与实现
  14. JBuilder2005+JBOSS+Oracle9i开发
  15. mysql4.1.10的JDBC驱动(mysql-co
  16. 在Win2003+Tomcat+MySQL下运行JP
  1. vb可不可以实现虚拟中断
  2. VB.NET中的组件开发
  3. 用vb编一个计算器,需要用到数组
  4. 如何用VB.Net创建一个三层的数据
  5. VB.Net的ByVal和ByRef --ByVal时
  6. VB.NET的阳历与农历转换的算法
  7. VB.NET操作SQL Server完全模块
  8. VB中定制DllRegisterServer、Dll
  9. VB中打印ACCESS报表
  10. 基于WebGIS的GPS系统的设计与实现
  11. JBuilder2005+JBOSS+Oracle9i开发
  12. mysql4.1.10的JDBC驱动(mysql-co
  13. 在Win2003+Tomcat+MySQL下运行JP
  14. (原创)当server碰到server,soc
  15. [自创]JCreator安装学习使用方法
  16. Jsp分页原代码,及用法

最近更新

  • 推荐阅读
  • DELPHI《Winsock完成端口模型-Delphi代码》Winsock完成端口模型-Delphi代码