//===========================================================================// // File: netnub.hpp // // Project: MUNGA real mode network nub // // Contents: Implementation details for the Affine matrices // //---------------------------------------------------------------------------// // Date Who Modification // // -------- --- ---------------------------------------------------------- // // 03/27/95 GAC Initial coding. // //---------------------------------------------------------------------------// // Copyright (C) 1994-1995, Virtual World Entertainment, Inc. // // All Rights reserved worldwide // // This unpublished sourcecode is PROPRIETARY and CONFIDENTIAL // //===========================================================================// #if !defined(NETNUB_HPP) # define NETNUB_HPP // Version number of the netcom common block #define NETCOM_VERSION 11 // Maximum size of send and receive buffers (one ethernet packet) #define MAX_TRANSFER_SIZE 0xFF00U #define SHARED_MEMORY_SIZE (MAX_TRANSFER_SIZE+4) // Function codes (set by protected mode app before calling our interrupt) #define NETNUB_UNDEFINED (-1) // Netnub sets this function code after each operation is done #define NETNUB_STATUS 0 // Lets the netnub run and return status #define NETNUB_SEND_PACKET 1 // Send the packet in the buffer #define NETNUB_RECEIVE_PACKET 2 // Return a packet in the buffer #define NETNUB_TCP_OPEN 3 // Opens a TCP stream to another computer #define NETNUB_TCP_LISTEN 4 // Queue's a TCP listen that we can accept a connection on #define NETNUB_TCP_CLOSE 5 // Closes a TCP stream #define NETNUB_RESOLVE_ADDRESS 6 // Resolves a text IP address into a 32 bit number #define NETNUB_CHECK_SOCKET 7 // Checks a socket to see if anyone has connected yet #define NETNUB_UDP_OPEN 8 // Opens a UDP socket #define NETNUB_UDP_READ 9 // Returns a UDP record #define NETNUB_UDP_SEND 10 // Returns a UDP record #define NETNUB_MARKER_TEXT 11 // Writes the text supplied to standard out #define NETNUB_OPEN_FILE 12 #define NETNUB_WRITE_FILE 13 #define NETNUB_CLOSE_FILE 14 #define NETNUB_MULTIPLE_SEND 15 // The has a request to send to multiple streams #define NETNUB_MULTIPLE_RECEIVE 16 // Request to receive from several streams at once #define NETNUB_SET_SWITCHES 17 // Set the netnub runtime switches #define NETNUB_READ_FILE 18 #define NETNUB_SEEK_FILE 19 #define NETNUB_TCP_TICK 20 // Status returns from the netnub #define NETNUB_PARTIAL_TRANSMIT (-5) // Some part of a packet was not sent (very fatal) #define NETNUB_DATA_DUMPED (-4) // Data was dumped on the floor to avoid blocking #define NETNUB_STREAM_DISCONNECTED (-3) // Stream has been disconnected at the remote end #define NETNUB_RESOLVE_ERROR (-2) // Unable to resolve an internet address #define NETNUB_ERROR (-1) // Unspecified error (something broke) #define NETNUB_OK 0 // No error (everything ok) #define NETNUB_RECEIVED_PACKET 1 // A packet has been received and is in the buffer #define NETNUB_TCP_CONNECTED 2 // Notifys us that someone connected to the socket // Netcom shared memory structure, used to pass commands and packets between the // real and protected mode part of the application. This structure should be // allocated in the real mode application. // // IMPORTANT: The Version Number field must stay in the same place and should be // checked by the protected mode app to make sure it was spawned by a real mode // server with a matching Version Number. This prevents the real and protected // mode applications from accidentally getting out of sync. // // NOTE: More data will eventually be added, but it will be at the END of the // structure so as not to mess up any machine code. struct Netcom { long Version_Number; // Version number of real mode netnub short Interrupt_Number, // Interrupt number to use for communcations Function, // * Function code (from protected mode app) Status; // * Current status of the netnub unsigned short Buffer_Length; // * Length of data in shared memory buffer char Shared_Memory_Buffer[SHARED_MEMORY_SIZE]; // * Data to send (from protected mode app) }; // NOTE: Fields marked with a * should be copied from real to protected mode, // the interrupt called, then on return they should be copied back. It is never // necessary to copy more than "Buffer_Length" bytes of the Shared_Memory_Buffer. // // Typedef for a pointer to the netcom structure typedef Netcom *Netcom_Ptr; //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Description of operations // // Regardless of what function is being sent, the machine code procedure // should always copy to real mode all the fields marked with a * before // calling the interrupt. On return from the interrupt all these fields should // be copied back from real to protected mode. It is never necessary to copy // more than "Buffer_Length" bytes of the Shared_Memory_Buffer. If "Buffer_Length" // is zero, the copy of shared memory should be skipped. // // For each function code there can be two structures. One will be the format // of data in the Shared_Memory_Buffer for a "request" and the other for a reply // to that request. Either may be omitted if not necessary. When Shared_Memory_Buffer // is received by either the protected mode or real mode part of the application // it will be "cast" into the proper structure based on the function code. // Note that some of these structures have only one data entry in them, they were // made structures to allow for future expansion. // // After processing each function the real mode netnub will set the Function // code to NETNUB_UNDEFINED so it can detect if the protected mode program // has forgotten to set the function code for any reason. // // A Function of NETNUB_RECEIVE_PACKET can result in either a packet or a connect // being returned. // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ struct SetSwitchesRequest { int blocking_switch; // Setting of the blocking/non blocking mode }; typedef SetSwitchesRequest *SetSwitchesRequestPtr; //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ struct StatusReturn { unsigned long My_Net_Address; }; typedef StatusReturn *StatusReturnPtr; //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Structure in Shared_Memory_Buffer for a receive data packet struct ReceivePacketRequest { unsigned long Socket_Ptr; // Socket pointer, see note above }; typedef ReceivePacketRequest *ReceivePacketRequestPtr; #define MAX_RECEIVE_DATA_SIZE 1600 //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ #define MULTIPLE_RECEIVE_PACKET_MAX 10 struct MultipleReceivePacketRequest { unsigned long // It's a long to insure structure alignment is predictable Socket_Count; // Number of sockets in the list below unsigned long Socket_Ptrs[MULTIPLE_RECEIVE_PACKET_MAX]; // Contains socket pointers }; typedef MultipleReceivePacketRequest *MultipleReceivePacketRequestPtr; struct MultipleReceivePacketReturn { unsigned long // It's a long to insure structure alignment is predictable Socket_Count; // Number of sockets in the list below unsigned long // long so it matches the format of MultipleSendPacketRequest Status[MULTIPLE_RECEIVE_PACKET_MAX]; // length or error code for this socket char Received_Data[4]; }; typedef MultipleReceivePacketReturn *MultipleReceivePacketReturnPtr; #define MULTIPLE_RECEIVE_BUFFER_SIZE(data_size) (data_size + sizeof(MultipleReceivePacketReturn)-4) #define MULTIPLE_RECEIVE_DATA_SIZE(buffer_size) (buffer_size - sizeof(MultipleReceivePacketReturn)+4) //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ struct SendPacketRequest { unsigned long Socket_Ptr; // Socket pointer, see note above char Send_Data[4]; // !!! set to 4 to insure word alignment }; #define SEND_BUFFER_SIZE(data_size) ((data_size) + sizeof(SendPacketRequest) - 4) #define SEND_DATA_SIZE(buffer_size) ((buffer_size) - sizeof(SendPacketRequest) + 4) #define MAX_SEND_DATA_SIZE (1604 - sizeof(SendPacketRequest)) struct SendPacketReturn { unsigned long Send_Buffer_Used; // Number of bytes in the send buffer }; typedef SendPacketReturn *SendPacketReturnPtr; typedef SendPacketRequest *SendPacketRequestPtr; //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // This command sends the same data to multiple destinations // #define MULTIPLE_SEND_PACKET_MAX 10 struct MultipleSendPacketRequest { unsigned long // It's a long to insure structure alignment is predictable Socket_Count; // Number of sockets to send to unsigned long Socket_Ptrs[MULTIPLE_SEND_PACKET_MAX]; // Contains socket pointers char Send_Data[4]; // !!! set to 4 to insure word alignment }; struct MultipleSendPacketReturn { unsigned long // It's a long to insure structure alignment is predictable Socket_Count; // Number of sockets to send to unsigned long // long so it matches the format of MultipleSendPacketRequest Errors[MULTIPLE_SEND_PACKET_MAX]; // Contains socket pointers unsigned long Send_Buffer_Used[MULTIPLE_SEND_PACKET_MAX]; // Number of bytes in the send buffer }; #define MULTIPLE_SEND_BUFFER_SIZE(data_size) (data_size + sizeof(MultipleSendPacketRequest) - 4) #define MULTIPLE_SEND_DATA_SIZE(buffer_size) (buffer_size - sizeof(MultipleSendPacketRequest) + 4) #define MAX_MULTIPLE_SEND_DATA_SIZE (MAX_TRANSFER_SIZE - sizeof(MultipleSendPacketRequest) + 4) typedef MultipleSendPacketRequest *MultipleSendPacketRequestPtr; typedef MultipleSendPacketReturn *MultipleSendPacketReturnPtr; //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ struct ResolveReturn { unsigned long Internet_Address; // 32 bit internet address (if no error) }; typedef ResolveReturn *ResolveReturnPtr; struct TCPOpenRequest { short Local_Port, // Local port number Remote_Port; // Remote port number unsigned long Internet_Address; // Internet address to connect with unsigned long Socket_Ptr; // tcp_Socket address (at least 4300 bytes) if 0 netnub will try to allocate one }; struct TCPOpenReturn { unsigned long Socket_Ptr; // pointer to the socket opened or error number }; typedef TCPOpenRequest *TCPOpenRequestPtr; typedef TCPOpenReturn *TCPOpenReturnPtr; struct TCPCloseRequest { unsigned long Socket_Ptr; // pointer to the socket to be closed }; typedef TCPCloseRequest *TCPCloseRequestPtr; struct TCPCheckSocketRequest { unsigned long Socket_Ptr; // pointer to the socket to be checked }; struct TCPCheckSocketReturn { unsigned long Socket_Net_Address; // Net address of the person who connected }; typedef TCPCheckSocketRequest *TCPCheckSocketRequestPtr; typedef TCPCheckSocketReturn *TCPCheckSocketReturnPtr; struct UDPOpenRequest { short Local_Port, // Local port number Remote_Port; // Remote port number unsigned long Internet_Address; // Internet address to connect with unsigned long Socket_Ptr; // UDP_Socket address (at least 2200 bytes) if 0 netnub will try to allocate one }; struct UDPOpenReturn { unsigned long Socket_Ptr; // pointer to the socket opened or error number }; typedef UDPOpenRequest *UDPOpenRequestPtr; typedef UDPOpenReturn *UDPOpenReturnPtr; struct OpenFileRequest { char File_Name[80]; short Access; unsigned short Model; }; struct OpenFileReturn { short File_Handle; }; typedef OpenFileRequest *OpenFileRequestPtr; typedef OpenFileReturn *OpenFileReturnPtr; struct CloseFileRequest { short File_Handle; }; typedef CloseFileRequest *CloseFileRequestPtr; struct WriteFileRequest { short File_Handle; unsigned short Write_Length; char Write_Data[4]; }; struct WriteFileReturn { unsigned short Bytes_Written; }; typedef WriteFileRequest *WriteFileRequestPtr; typedef WriteFileReturn *WriteFileReturnPtr; struct ReadFileRequest { short File_Handle; unsigned short Read_Length; }; struct ReadFileReturn { char Read_Data[4]; }; typedef ReadFileRequest *ReadFileRequestPtr; typedef ReadFileReturn *ReadFileReturnPtr; struct SeekFileRequest { short File_Handle; short Seek_Mode; long Seek_Offset; }; struct SeekFileReturn { long Seek_Position; }; typedef SeekFileRequest *SeekFileRequestPtr; typedef SeekFileReturn *SeekFileReturnPtr; #endif