⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 tcp.c

📁 采用Fork方式的
💻 C
字号:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <signal.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <netdb.h>
#include <time.h>
#include "applib.h"

static int Handle = -1;
static int Socket = -1;
static int Timeout = 0;

static void TCPClose( int h )
{
  if( h >= 0 ){
    close( h );
    h = -1;
  }
}

static int TCPError( int r )
{
  TCPExit();
  return( r );
}

static int TCPInit( char *N, struct sockaddr_in *S, unsigned long R )
{
  struct servent *sp;
  int s;
  unsigned short p;

  if( ( sp = getservbyname( N, "tcp" ) ) != NULL )
    p = sp->s_port;
  else if( ( p = htons( atoi( N ) ) ) == 0 )
    return( -88888 );
  if( ( s = socket( AF_INET, SOCK_STREAM, 0 ) ) < 0 )
    return( -99999 );
  bzero( ( char * ) S, sizeof( struct sockaddr_in ) );
  S->sin_family = AF_INET;
  S->sin_addr.s_addr = R;
  S->sin_port = p;
  return( s );
}

void TimedWrite( int Seconds )
{
  Timeout = Seconds;
}

int TCPCall( char *Service, char *Remote )
{
  struct sockaddr_in sin;
  struct hostent *hp;
  unsigned long a;

  if( ( hp = gethostbyname( Remote ) ) != NULL )
    a = *( ( unsigned long * ) hp->h_addr );
  else if( ( a = inet_addr( Remote ) ) == INADDR_NONE )
    return( -4 );
  if( ( Handle = TCPInit( Service, &sin, a ) ) < 0 )
    return( Handle );
  if( connect( Handle, ( struct sockaddr * )&sin, sizeof( sin ) ) < 0 )
    return( TCPError( -3 ) );
  return( 0 );
}

static int TCPAccept( char *Service, int Multi )
{
  struct sockaddr_in sin, from;
  int l = sizeof( from );
  int s = 1;

  if( !Service ){
    Handle = 0;
    return( 0 );
  }
  if( Multi )
    signal(SIGCLD, SIG_IGN);
  if( ( Socket = TCPInit( Service, &sin, htonl( INADDR_ANY ) ) ) < 0 )
    return( Socket );
  if( setsockopt( Socket, SOL_SOCKET, SO_REUSEADDR, &s, sizeof( s ) ) < 0 )
    return( TCPError( -6 ) );
  if( setsockopt( Socket, SOL_SOCKET, SO_REUSEPORT, &s, sizeof( s ) ) < 0 )
    return( TCPError( -7 ) );
  if( bind( Socket, ( struct sockaddr * )&sin, sizeof( sin ) ) < 0 )
    return( TCPError( -3 ) );
  if( listen( Socket, 5 ) < 0 )
    return( TCPError( -5 ) );
  while( 1 ){
    if( ( Handle = accept( Socket, ( struct sockaddr * )&from, &l ) ) >= 0 ){
      if( !Multi || fork() == 0 ){
        TCPClose( Socket );
        return( 0 );
      }
      TCPClose( Handle );
    }
    else if( !Multi )
      return( TCPError( -8 ) );
  }
}

int TCPAnswer( char *Service )
{
  return( TCPAccept( Service, 1 ) );
}

int TCPLink( char *Service )
{
  return( TCPAccept( Service, 0 ) );
}

int TCPPeer( char *IPABuf )
{
  struct sockaddr_in s;
  int l = sizeof( s );

  if( Handle < 0 )
    return( -1 );
  if( IPABuf ){
    if( getpeername( Handle, ( struct sockaddr * ) &s, &l ) )
      return( -1 );
    strcpy( IPABuf, ( char * ) inet_ntoa( s.sin_addr.s_addr ) );
  }
  return( 0 );
}

int TCPWrite( void *Data, int Size )
{
  return( TimedWrite( Timeout, Handle, Data, Size ) );
}

int TCPRead( void *Data, int Size )
{
  return( TimedRead( Timeout, Handle, Data, Size ) );
}

void TCPExit()
{
  TCPClose( Handle );
  TCPClose( Socket );
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -