// ===================================================
// Листинг 5. Клиент IPX
//
// Файл ipxclien.c
//
// (C) A. Frolov, 1993
// ===================================================

#include <stdio.h>
#include <stdlib.h>
#include <conio.h>
#include <mem.h>
#include <string.h>
#include "ipx.h"

// Максимальный размер буфера данных

#define BUFFER_SIZE 512

void main(void) {

// Будем работать с сокетом 0x4567

	static unsigned Socket = 0x4567;

// ECB для приема и передачи пакетов

	struct ECB RxECB, TxECB;

// Заголовки принимаемых и передаваемых пакетов

	struct IPX_HEADER RxHeader, TxHeader;

// Буфера для принимаемых и передаваемых данных

	unsigned char RxBuffer[BUFFER_SIZE];
	unsigned char TxBuffer[BUFFER_SIZE];

	printf("\n*Клиент IPX*, (C) Фролов А., 1993\n\n");

// Проверяем наличие драйвера IPX и определяем
// адрес точки входа его API

	if(ipx_init() != 0xff) {
		printf("IPX не загружен!\n"); exit(-1);
	}

// Открываем сокет, на котором мы будем
// принимать и передавать пакеты

	if(IPXOpenSocket(SHORT_LIVED, &Socket)) {
		printf("Ошибка при открытии сокета\n");
		exit(-1);
	};

// Подготавливаем ECB для передачи пакета

	memset(&TxECB, 0, sizeof(TxECB));

	TxECB.Socket            = IntSwap(Socket);
	TxECB.FragmentCnt       = 2;
	TxECB.Packet[0].Address = &TxHeader;
	TxECB.Packet[0].Size    = sizeof(TxHeader);
	TxECB.Packet[1].Address = TxBuffer;
	TxECB.Packet[1].Size    = BUFFER_SIZE;

// Пакет предназначен всем станциям данной сети

	memset(TxECB.ImmAddress, 0xff, 6);

// Подготавливаем заголовок пакета

	TxHeader.PacketType = 4;
	memset(TxHeader.DestNetwork, 0, 4);
	memset(TxHeader.DestNode, 0xff, 6);
	TxHeader.DestSocket = IntSwap(Socket);

// Записываем передаваемые данные

	strcpy(TxBuffer, "CLIENT *DEMO*");

// Передаем пакет всем станциям в данной сети

	IPXSendPacket(&TxECB);

// Подготавливаем ECB для приема пакета от сервера

	memset(&RxECB, 0, sizeof(RxECB));
	RxECB.Socket            = IntSwap(Socket);
	RxECB.FragmentCnt       = 2;
	RxECB.Packet[0].Address = &RxHeader;
	RxECB.Packet[0].Size    = sizeof(RxHeader);
	RxECB.Packet[1].Address = RxBuffer;
	RxECB.Packet[1].Size    = BUFFER_SIZE;

	IPXListenForPacket(&RxECB);

	printf("Ожидание ответа от сервера\n");
	printf("Для отмены нажмите любую клавишу\n");


// Ожидаем прихода ответа от сервера

	while(RxECB.InUse) {
		IPXRelinquishControl();
		if(kbhit()) {
			getch();
			RxECB.CCode = 0xfe;
			break;
		}
	}
	if(RxECB.CCode == 0) {
		printf("Принят ответ от сервера '%s'\n", RxBuffer);
	}

// Закрываем сокет

	IPXCloseSocket(&Socket);
	exit(0);
}