From 90b1b10207d01035b6ab4be08dfddbd8024fa023 Mon Sep 17 00:00:00 2001 From: Viktor Szakats Date: Sun, 1 Feb 2009 09:21:46 +0000 Subject: [PATCH] 2009-02-01 10:21 UTC+0100 Viktor Szakats (harbour.01 syenar hu) + doc/inet.txt + Added from xhb. --- harbour/ChangeLog | 4 + harbour/doc/inet.txt | 363 +++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 367 insertions(+) create mode 100644 harbour/doc/inet.txt diff --git a/harbour/ChangeLog b/harbour/ChangeLog index 3cfbc188da..59284008d6 100644 --- a/harbour/ChangeLog +++ b/harbour/ChangeLog @@ -8,6 +8,10 @@ 2008-12-31 13:59 UTC+0100 Foo Bar (foo.bar foobar.org) */ +2009-02-01 10:21 UTC+0100 Viktor Szakats (harbour.01 syenar hu) + + doc/inet.txt + + Added from xhb. + 2009-01-31 20:43 UTC+0100 Viktor Szakats (harbour.01 syenar hu) * contrib/gtwvg/tests/demoxbp.prg + Added SVN header. diff --git a/harbour/doc/inet.txt b/harbour/doc/inet.txt new file mode 100644 index 0000000000..499b2608f8 --- /dev/null +++ b/harbour/doc/inet.txt @@ -0,0 +1,363 @@ +/* + * $Id$ + */ + + HARBOUR INET API + ------------------ + + + Giancarlo Niccolai + +/* $DOC$ + * $FUNCNAME$ + * harbour Inet functions + * $CATEGORY$ + * harbour Enhacements + * $ONELINER$ + * HARBOUR INET API + * $DESCRIPTION$ + * + * STATUS OF THIS DOCUMENT + * + * + * This is just a draft, a survival guide with minimal API instructions + * extracted from the inet.c program comments and from some posting to + * the xharbour newsgroup. + * + * More adequate version will be available soon. + * + * + * HARBOUR INET API + * ================ + * + * + * Startup / cleanup functions + * --------------------------- + * + * hb_InetInit() -->NIL + * Activates inet support; mainly used for winsock start up at the moment, but + * could be used in the future for many other purpose. Put it at the beginning + * of every program using INET functions. + * + * + * hb_InetCleanup() -->NIL + * Closes Inet support; mainly used for win32. Put it at the end of any program + * using Inet functions, just before the program exits. + * + * hb_InetCreate() --> SOCKET + * Creates the raw data of the socket, that can be passed to an asynchronous + * connection function (hb_InetConnect or hb_InetConnectIP). This will prevent the + * connection function from allocating some data that could be never used in + * certain cases, i.e. an asynchronously detected timeout. + * + * hb_InetClose( SOCKET ) --> NUMERIC + * Closes the socket, notifiying both ends of the communication pipe that the + * connection is over. If you have threads waiting for data to be read from + * this socket, this method will make them stop waiting and return an error + * (socket closed) to their callers. + * The method does not destroy the socket, which can be used by subordinate + * threads to check that the socket is closed, and so they should stop as soon + * as they can. Don't destroy the socket unless you are sure that no other + * thread is using it. + * RETURNS 0 on success or -1 on error; on error, the error code is set; + * (actually, on success the socket error code is set to 1 -- socket closed ) + * + * + * hb_InetDestroy( SOCKET ) --> Numeric + * Closes AND destroys a socket. After this call, the socket can't be used + * anymore. Returns 0 on success -1 on failure. + * + * + * hb_InetSetTimeout( SOCKET, nMillisecs ) --> NIL + * Sets the default timeout of the given socket. Default timeout is used in all + * blocking operations: if the operation can't be done in nMillisec milliseconds, + * the function returns immediately and the hb_InetErrorCode( SOCKET ) returns -1. + * The default timeout is not the maximum time that a function using the socket + * is allowed to execute: it is the maximum time that each single blocking + * operation inside that function is allowed to hold the control of the socket. + * So, an function like hb_InetReadAll(), that may repeat a raw recv() several + * times, is not guaranteed to terminate in nMillisecs, but you are guaranteed + * that if any of that raw socket read operation is going to take more than + * nMillisecs, the function will be terminated. + * When created, a socket is created with an infinite default timeout (-1). + * + * hb_InetGetTimeout( SOCKET ) --> NUMERIC + * Returns the timeout set for the given socket. + * + * hb_InetClearTimeout( SOCKET, nMillisecs ) --> NIL + * Clears the default timeout of the given socket. Default timeout is used in all + * blocking operations. + * + * + * Informative functions + * --------------------- + * + * hb_InetErrorCode( SOCKET ) --> Numeric + * Returns the last error code that has been provoked by a network operation, + * or 0 if none. Error codes are the ones used for winsock or UnixSockets (they + * are the same); 1 is reserved for "connection closed" message. + * + * + * hb_InetErrorDesc( SOCKET ) --> String + * Returns a string describing the last error that occurred in the socket; + * the string is system dependent, and should be used only for debugging + * purposes. + * + * + * hb_InetCount( SOCKET ) --> Numeric + * Returns the amount of characters read or written in the latest socket + * operation. + * + * + * hb_InetAddress( SOCKET ) --> STRING + * Returns a string representing the remote server address in quad dot notation, + * e.g. "192.168.1.1", or the local server address if the socket is server + * side. + * TODO: have a version that returns a vector of 4 numbers. + * + * + * hb_InetPort( SOCKET ) --> STRING + * Returns the port to which this socket is bound, or the remote port if this + * socket is connected with a remote host or client + * + * Server Side socket functions + * ---------------------------- + * + * hb_InetServer( port [, cBindAddr [, nListenLimit]] ) --> SOCKET + * Creates a server that can accept connections from client on a certain port. + * If the computer on which hb_InetServe is called has more than one logical + * interface (e.g. one network card, one loopback and one PPP address), + * cBindAddr can be specified to select only one of these interfaces to accept + * connections for this process. This is useful when a server is present on + * two networks, and the service is to be available only in one of them. Also, + * the same port on other addresses is left free to be used, so you can have + * different server programs running for different networks but managing + * the same service. In example, an FTP server available to the internal + * network could be radically different from an FTP server available for + * the internet. + * nListenLimit is an internal parameter and rarely needs to be specified. + * This is the number of incoming connections accepted by kernel before the + * kernel has the chance to report them to the application program. If + * the sockets receive nListenLimit connections before accepting them + * all, the nListenLimit + 1 connection will be notified to be "busy" by + * the kernel. Usually, a value of 10 (the default) is enough for even + * a heavy duty server. + * On error, sets error description in the newly returned socket. + * + * hb_InetAccept( SOCKET ) --> SOCKET + * Waits until a connection is available on a socket created with hb_InetServer; + * Returns a socket that can be used to communicate with the incoming client. + * On error, sets error in the newly returned socket. + * + * Client side socket functions + * ---------------------------- + * + * hb_InetConnect( cAddress, nPort ) --> SOCKET + * hb_InetConnect( cAddress, nPort, SOCKET ) --> NIL + * Connects to a remote server described by cAddress, that can be in + * quad dot notation (e.g. "192.168.1.1") or in DNS name (e.g. + * "www.xharbour.org"), using the desired port. + * hb_InetConnect uses "gethostbyname" C system call to + * find the network address of the specified server; this means that + * this call is an hybrid function doing both a DNS scan and a TCP/IP + * connection. hb_InetConnect is not thread safe, and the xHarbour + * program must take care that two hb_InetConnect functions are never + * called at the same moment from two different threads (or that + * hb_InetGetHosts is not called in the same moment as an hb_InetConnect). + * The second version of this function accepts a pre-built socket + * as a parameter. This allows to kill asyncronously a thread waiting + * for hb_InetConnect to connect, and then cleaning up the leftover + * socket data. Also, it is possible to give timeout to the given SOCKET, + * but this timeout will be used only in the connection phase, after that + * the network address resolution is completed. Use GetHosts() and + * hb_InetConnectIP for a finer timeout control. + * On error, the error of the returned socket is set. The error could + * be due to unavailable name resolving service, host name not valid, + * host address not reachable and host reachable but port not open. + * + * + * hb_InetConnectIP( cAddress, PORT ) --> SOCKET + * hb_InetConnectIP( cAddress, PORT, SOCKET ) --> NIL + * Connects to a remote server described by cAddress, that can be specified + * only in quad dot IPV4 notation (e.g. "127.0.0.1"), using the desired port. + * This version of hb_InetConnect does not use gethostbyname, and thus is thread + * safe and can be used in combination with hb_InetGetHosts to have a finer + * timeout control while connecting to a server, and a finer error control. + * The second version of this function accepts a pre-built socket + * as a parameter. This allows to kill asyncronously a thread waiting + * for hb_InetConnectIP to connect, and then cleaning up the leftover + * socket data. Also, it is possible to give timeout at the given SOCKET. + * + * On error, the error of the returned socket is set. + * + * + * + * Sending and receiving data + * ---------------------------- + * + * hb_InetRecv( SOCKET, @cString [, nAmount] ) --> NUMERIC + * Reads at maximum nAmount bytes (or a number of bytes equal to cString + * length if nAmount is not given) from the socket into cString. + * The parameter cString must be preallocated so that it has enough + * space to receive the data. The routine will block the thread until some + * bytes are read from the socket, the socket is closed (either from the + * receiver or the sender side) or a network error occurs, whichever comes + * first. In the latter cases, an error is set, and only the characters + * received until premature end of communications are returned. + * Notice that there is no guarantee that all the available bytes will be + * read before the function returns, in fact, hb_InetRecv returns as soon it + * is able to fill cString with one or more bytes. To block the current + * process until the whole cString is filled (or nAmount bytes are read), + * use the hb_InetRecvALL(). + * RETURNS the number of the characters read from the SOCKET. + * + * + * hb_InetRecvAll( SOCKET, @cString [, @nAmount] ) --> NUMERIC + * This function works exactly as hb_InetRecv, except for the fact that it + * blocks until nAmount bytes are read, if nAmount is given, or + * cString is filled for its whole length. + * RETURNS the number of the characters read from the SOCKET. Might be + * less than nAmount on premature socket closing or on network error. + * + * + * hb_InetRecvLine( SOCKET [, @nResult, [, nMaxLength [, nBufSize]]] ) --> STRING + * Blocks the calling thread until a sequence CRLF is read from the socket. + * Incremental allocation and end-of-line checking are done in an efficient + * way. If an error occurs, or if the stream is closed before a CRLF is read, + * the function returns nothing and sets the socket error. + * The returned string does not contain the trailing CRLF sequence, so an + * empty line is effectively returned as an empty string. + * If the nResult parameter is given, it will contain the number of bytes + * read from the socket, including the CRLF sequence, so that in normal + * conditions, nResult will report a count equal to the length of the + * returned string plus 2. nResult will be 0 if stream is closed before + * a CRLF sequence is read, and will be -1 on error. + * An optional MaxLength parameter can be given to allow a maximum character + * count before the data is returned anyway. If this number is hit before + * a CRLF sequence is encountered, nResult will contain the value one. + * Finally, a nBufSize parameter can be given. If not, memory allocation + * will be increased by discrete amounts of 80 bytes. The programmer + * can provide here a different allocation strategy (e.g. setting nBufSize + * equal to nMaxLength, memory for reading the line will be allocated only + * once, at the beginning of the function). + * + * + * hb_InetRecvEndBlock( SOCKET [, cBlock [, @nResult, [, nMaxLength [, + * nBufSize]]]] ) --> STRING + * This function operates exactly the same way as hb_InetRecvLine, but + * the "record termination" is customizable thorugh the cBlock parameter. + * If not given, this parameter defaults to the CRLF sequence. + * Provided by: Marcelo Lombardo + * + * + * hb_InetDataReady( SOCKET [, nMillisecs] ) --> NUMERIC + * Verifies if some data is available to be read in the socket without blocking + * execution of the caller. If nMillisecs is not given, the function returns + * immediately 1 if there is some data to be read, 0 if there isn't any data and + * -1 in case of error. If nMillisecs is given, the functon will wait up to that + * amount of milliseconds for data to be available; if some data arrives in the + * meanwhile, the wait is immediately interrupted. + * The next hb_InetRecv() function will read all the available data (up to the + * required length) without blocking. + * On error, hb_InetErrorCode and hb_InetErrorDesc can be use to determine what kind + * of error happened. + * + * + * hb_InetSend( SOCKET, STRING [, nLength ] ) --> NUMERIC + * Send data being stored in a string over the socket. Returns the amount of + * data written, 0 if the socket has been closed in the meanwhile or -1 on + * error. The nLength parameter can be given to allow writing only a part of + * the string. + * Please, notice that there is no guarantee that all your string will be + * sent, as this is a decision that is up to the OS; this function does not + * take care to ensure that the data is really sent; so you should check for + * the returned number, and send the part that has not been sent. + * To ensure that all the data is sent before the function returns, use the + * hb_InetSendAll() function. + * On error, the error in the socket is set. + * + * + * hb_InetSendAll( SOCKET, STRING [, nLength ] ) --> NUMERIC + * This function works exactly as hb_InetSend() but it ensures that all the + * data to be sent is written before returning. + * + * Utility Functions + * ------------------ + * + * hb_InetGetHosts( cName ) --> aHosts + * Returns an array containing all the IP addresses associated with a given + * host name. The IP addressess returned by this funtion are strings in + * quad dot notations, eg "192.168.1.1", and can be directly used into + * hb_InetConnectIP(). cName can be any string: valid DNS names (eg. + * "www.myserver.com"), locally available names (e.g. "localhost" or + * windows Network Neighborhood names), or even IP addresses in quad + * dot notation. + * NOTE: This function is not thread safe (by design), and programmers + * must be sure not to use it at the same time in two different threads, + * or not to use it together with a hb_InetConnect(). If this kind of situation + * should ever arise, you are advised to use a thread MUTEX. + * On error, and if the server can't be found, the function returns NIL. + * + * + * hb_InetGetAlias( cName ) --> aHosts + * Returns an array containing the aliases ( CNAME DNS records ) by + * which the server is currently known. Whether this function is able + * to have the complete list of aliases or not depends on the verbosity + * of the DNS server. + * + * + * hb_InetCRLF() --> String + * Returns a CRLF sequence used in many internet protocols. + * + * UDP (User Datagram Protocol) Compliant Routines + * ----------------------------------------------- + * + * hb_InetDGram( [bBroadcast] ) --> SOCKET + * Creates a datagram oriented socket that will be able to send data and + * eventually receive data. Since the socket is not bound, the program can't + * retrieve the address at which this socket appaers to be, but a second + * socket receiving a message sent from this one would be able to reply + * correctly with a datagram that can be read from a non-bound socket. + * If bBroadcast is set to .T., the routine creates a broadcast capable socket: + * it will be able to receive and send broadcast messages. On most systems this + * requires special user privileges. + * Returns the socket, and if an error occurs, the socket error message + * and code are set. + * + * + * hb_InetDGramBind( nPort, [cAddress [, bBroadcast] ] ) --> SOCKET + * Creates a datagram oriented socket and binds it to a particular port, and + * eventually to a certain interface if cAddress is given and not NIL. + * If bBroadcast is set to .T., the routine creates a broadcast capable socket: + * it will be able to receive and send broadcast messages. On most systems this + * requires special user privileges. + * Returns the socket, and if an error occurs, the socket error message + * and code are set. + * + * + * hb_InetDGramSend( SOCKET, cAddress, nPort, cBuffer [, nSize ] ) --> NUMERIC + * Sends a datagram (a fixed length data) to a determined ip address (cAddress, + * to be specified in quad-dot notation) and port. If nSize is not specified, + * all the data in cBuffer will be sent; if nSize is specified, only + * the first nSize bytes of cBuffer will be sent. + * There isn't any guarantee that all the data required to be written is + * really sent to the socket: the calling program should check for the + * numeric return and send iteratively the unsent data to complete + * the message. + * Anyway, the raw datagram is sent and received as once, and any data + * less than the system datagram size will be sent and received + * as a single item. + * If the socket is created in broadcast mode, the cAddress element + * can be a broadcast address. + * Returns -1 on error, or the number of bytes actually sent on success. + * + * hb_InetDGramRecv( SOCKET, cBuffer [, nSize ] ) --> NUMERIC + * Reads at maximum nSize bytes incoming from a UDP socket, if nSize is + * given, or reads at maximum cBuffer length if nSize is not given. + * There isn't any guarantee that all the data required to be read is + * really sent from the kernel to the application: the kernel should + * just return the last complete datagram that has been received, up + * to nSize bytes. + * Returns -1 on error, or the number of bytes actually read on success. + * $END$ + */