2010-11-26 13:44 UTC+0100 Viktor Szakats (harbour.01 syenar.hu)

* include/hbapi.h
  * src/common/hbver.c
    + Added hb_iswin2k3().

  * src/rtl/hbsocket.c
    + Comment.
    ; TOFIX: Use SO_EXCLUSIVEADDRUSE on Windows.
             See: http://paste.lisp.org/display/59751

  - examples/udpds
  + contrib/hbmisc/tests/udpdstst.prg
  + contrib/hbmisc/udpds.prg
  * contrib/hbmisc/hbmisc.hbp
    + Moved UDPDS functions to hbmisc lib. Added hb_ prefix to names,
      plus formatted with hbformat.

  * contrib/hbhttpd/tests/webapp.prg
    * Formatting.

  ; Patch from Tamas:

  * config/bsd/gcc.mk
  * config/bsd/clang.mk
    * switch bsd to -fPIC, otherwise not even core builds (on 8.1/amd64)
    * while there, bring bsd/gcc.mk in line with linux/gcc.mk (now they
      are identical)
    * ditto for bsd/clang.mk

  * contrib/hbqt/hbqt_common.hbc
    * for hbqt, switch static supc++ to dynamic stdc++, otherwise dyn hbqt
      doesn't build. this is because on at least fbsd supc++ is apparently
      not pic; but switching from static supc++ to dynamic stdc++ easily
      fixes it.
This commit is contained in:
Viktor Szakats
2010-11-26 12:46:14 +00:00
parent 7c8c239f5c
commit 4a22ee33f7
13 changed files with 228 additions and 171 deletions

View File

@@ -16,6 +16,41 @@
The license applies to all entries newer than 2009-04-28.
*/
2010-11-26 13:44 UTC+0100 Viktor Szakats (harbour.01 syenar.hu)
* include/hbapi.h
* src/common/hbver.c
+ Added hb_iswin2k3().
* src/rtl/hbsocket.c
+ Comment.
; TOFIX: Use SO_EXCLUSIVEADDRUSE on Windows.
See: http://paste.lisp.org/display/59751
- examples/udpds
+ contrib/hbmisc/tests/udpdstst.prg
+ contrib/hbmisc/udpds.prg
* contrib/hbmisc/hbmisc.hbp
+ Moved UDPDS functions to hbmisc lib. Added hb_ prefix to names,
plus formatted with hbformat.
* contrib/hbhttpd/tests/webapp.prg
* Formatting.
; Patch from Tamas:
* config/bsd/gcc.mk
* config/bsd/clang.mk
* switch bsd to -fPIC, otherwise not even core builds (on 8.1/amd64)
* while there, bring bsd/gcc.mk in line with linux/gcc.mk (now they
are identical)
* ditto for bsd/clang.mk
* contrib/hbqt/hbqt_common.hbc
* for hbqt, switch static supc++ to dynamic stdc++, otherwise dyn hbqt
doesn't build. this is because on at least fbsd supc++ is apparently
not pic; but switching from static supc++ to dynamic stdc++ easily
fixes it.
2010-11-26 12:55 UTC+0100 Przemyslaw Czerpak (druzus/at/priv.onet.pl)
* harbour/src/rdd/dbf1.c
* harbour/src/rdd/sdf1.c

View File

@@ -18,6 +18,8 @@ OBJ_EXT := .o
LIB_PREF := lib
LIB_EXT := .a
HB_DYN_COPT := -DHB_DYNLIB -fPIC
CC := $(HB_CCACHE) $(HB_CCPREFIX)$(HB_CMP)$(HB_CCPOSTFIX)
ifneq ($(filter --analyze, $(HB_USER_CFLAGS)),)
CC_IN :=
@@ -58,17 +60,6 @@ DFLAGS += -shared $(LIBPATHS)
DY_OUT := -o$(subst x,x, )
DLIBS := $(foreach lib,$(HB_USER_LIBS) $(SYSLIBS),-l$(lib))
# NOTE: The empty line directly before 'endef' HAVE TO exist!
define dynlib_object
@$(ECHO) $(ECHOQUOTE)INPUT($(subst \,/,$(file)))$(ECHOQUOTE) >> __dyn__.tmp
endef
define create_dynlib
$(if $(wildcard __dyn__.tmp),@$(RM) __dyn__.tmp,)
$(foreach file,$^,$(dynlib_object))
$(DY) $(DFLAGS) $(HB_USER_DFLAGS) $(DY_OUT)$(DYN_DIR)/$@ __dyn__.tmp $(DLIBS) $(DYSTRIP)
endef
DY_RULE = $(create_dynlib)
DY_RULE = $(DY) $(DFLAGS) $(HB_USER_DFLAGS) $(DY_OUT)$(DYN_DIR)/$@ $^ $(DLIBS) $(DYSTRIP) && $(LN) $(@F) $(DYN_FILE2)
include $(TOP)$(ROOT)config/rules.mk

View File

@@ -2,16 +2,20 @@
# $Id$
#
ifeq ($(HB_BUILD_MODE),cpp)
HB_CMP := g++
else
HB_CMP := gcc
ifeq ($(HB_CMP),)
ifeq ($(HB_BUILD_MODE),cpp)
HB_CMP := g++
else
HB_CMP := gcc
endif
endif
OBJ_EXT := .o
LIB_PREF := lib
LIB_EXT := .a
HB_DYN_COPT := -DHB_DYNLIB -fPIC
CC := $(HB_CCACHE) $(HB_CCPREFIX)$(HB_CMP)$(HB_CCPOSTFIX)
CC_IN := -c
CC_OUT := -o
@@ -48,17 +52,6 @@ DFLAGS += -shared $(LIBPATHS)
DY_OUT := -o$(subst x,x, )
DLIBS := $(foreach lib,$(HB_USER_LIBS) $(SYSLIBS),-l$(lib))
# NOTE: The empty line directly before 'endef' HAVE TO exist!
define dynlib_object
@$(ECHO) $(ECHOQUOTE)INPUT($(subst \,/,$(file)))$(ECHOQUOTE) >> __dyn__.tmp
endef
define create_dynlib
$(if $(wildcard __dyn__.tmp),@$(RM) __dyn__.tmp,)
$(foreach file,$^,$(dynlib_object))
$(DY) $(DFLAGS) $(HB_USER_DFLAGS) $(DY_OUT)$(DYN_DIR)/$@ __dyn__.tmp $(DLIBS) $(DYSTRIP)
endef
DY_RULE = $(create_dynlib)
DY_RULE = $(DY) $(DFLAGS) $(HB_USER_DFLAGS) $(DY_OUT)$(DYN_DIR)/$@ $^ $(DLIBS) $(DYSTRIP) && $(LN) $(@F) $(DYN_FILE2)
include $(TOP)$(ROOT)config/rules.mk

View File

@@ -94,17 +94,17 @@ FUNCTION Main()
aMap := {;
"login" => @proc_login(), ;
"logout" => @proc_logout(), ;
"register" => @proc_register(), ;
"account" => @proc_account(), ;
"account/edit" => @proc_account_edit(), ;
"main" => @proc_main(), ;
"shopping" => @proc_shopping(), ;
"cart" => @proc_cart() }
"login" => @proc_login(), ;
"logout" => @proc_logout(), ;
"register" => @proc_register(), ;
"account" => @proc_account(), ;
"account/edit" => @proc_account_edit(), ;
"main" => @proc_main(), ;
"shopping" => @proc_shopping(), ;
"cart" => @proc_cart() }
oServer:aMount := {;
"/hello" => { {|| UWrite( "Hello!")}, .F. }, ;
"/hello" => { {|| UWrite( "Hello!" ) }, .F. }, ;
"/info" => { {|| UProcInfo() }, .F. }, ;
"/files/*" => { {|x| UProcFiles( hb_dirBase() + "files/" + x, .F. ) }, .F. }, ;
"/app/*" => { {|x| UProcWidgets( x, aMap ) }, .T. }, ;

View File

@@ -28,3 +28,4 @@ numtxthu.prg
numtxten.prg
stringp.prg
twirler.prg
udpds.prg

View File

@@ -0,0 +1,42 @@
/*
* $Id$
*/
/*
* This module demonstrates a simple UDP Discovery Server
*/
PROCEDURE main( cParam )
LOCAL h
IF ! hb_MTVM()
? "This sample should be compiled using MultiThread"
RETURN
ENDIF
IF cParam == NIL
? "udpdstst {c|s|cs}"
? "Parameter:"
? " s - run as a server"
? " c - run as a client"
RETURN
ENDIF
IF "S" $ Upper( cParam )
IF ! Empty( h := hb_UDPDS_Start( 39999, "UDPDSDemo", NetName() + " " + hb_TSToStr( hb_DateTime() ) ) )
hb_idleSleep( 0.1 )
ENDIF
ENDIF
IF "C" $ Upper( cParam )
? HB_VALTOEXP( hb_UDPDS_Find( 39999, "UDPDSDemo" ) )
ENDIF
IF "S" $ Upper( cParam )
? "Press any key to stop server"
Inkey( 0 )
hb_UDPDS_Stop( h )
ENDIF
RETURN

View File

@@ -0,0 +1,97 @@
/*
* $Id$
*/
/*
* This module demonstrates a simple UDP Discovery Server
*
* If you run some service on the network (ex., netio) you need to
* know server IP address and configure client to connect to this
* address. UDPDS helps client to find server address (or addresses
* of multiple servers) on local network. UDPDS should be run in
* parallel to real server (ex., netio). Server part of UDPDS uses
* threads, so, it should be compiled in MT mode.
*
* Server functions:
* hb_UDPDS_Start( nPort, cName [, cVersion ] ) --> hServer
* hb_UDPDS_Stop( hServer )
*
* Client function:
* hb_UDPDS_Find( nPort, cName ) --> { { "ip_addr_1", "version_1" }, ... }
*
*/
#include "hbsocket.ch"
/* Client */
FUNCTION hb_UDPDS_Find( nPort, cName )
LOCAL hSocket, aRet, nEnd, nTime, cBuffer, nLen, aAddr
IF ! Empty( hSocket := hb_socketOpen( , HB_SOCKET_PT_DGRAM ) )
hb_socketSetBroadcast( hSocket, .T. )
IF hb_socketSendTo( hSocket, Chr( 5 ) + cName + Chr( 0 ), , , { HB_SOCKET_AF_INET, "255.255.255.255", nPort } ) == Len( cName ) + 2
nTime := hb_milliseconds()
nEnd := nTime + 100 /* 100ms delay is enough on LAN */
aRet := {}
DO WHILE nEnd > nTime
cBuffer := Space( 2000 )
nLen := hb_socketRecvFrom( hSocket, @cBuffer, , , @aAddr, nEnd - nTime )
IF Left( cBuffer, Len( cName ) + 2 ) == Chr( 6 ) + cName + Chr( 0 )
AAdd( aRet, { aAddr[ 2 ], SubStr( cBuffer, Len( cName ) + 3, nLen - Len( cName ) - 2 ) } )
ENDIF
nTime := hb_milliseconds()
ENDDO
ENDIF
hb_socketClose( hSocket )
ENDIF
RETURN aRet
/* Server */
FUNCTION hb_UDPDS_Start( nPort, cName, cVersion )
LOCAL hSocket
IF ! Empty( hSocket := hb_socketOpen( , HB_SOCKET_PT_DGRAM ) )
IF hb_socketBind( hSocket, { HB_SOCKET_AF_INET, "0.0.0.0", nPort } )
hb_threadDetach( hb_threadStart( @UDPDS(), hSocket, cName, cVersion ) )
RETURN hSocket
ENDIF
hb_socketClose( hSocket )
ENDIF
RETURN NIL
PROCEDURE hb_UDPDS_Stop( hSocket )
hb_socketClose( hSocket )
RETURN
STATIC PROCEDURE UDPDS( hSocket, cName, cVersion )
LOCAL cBuffer, nLen, aAddr
DO WHILE .T.
cBuffer := Space( 2000 )
nLen := hb_socketRecvFrom( hSocket, @cBuffer, , , @aAddr, 1000 )
IF nLen == - 1
IF hb_socketGetError() != HB_SOCKET_ERR_TIMEOUT
RETURN
ENDIF
ELSE
/*
* Communication protocol:
* Broadcast request: ENQ, ServerName, NUL
* Server response: ACK, ServerName, NUL, Version
*/
IF Left( cBuffer, nLen ) == Chr( 5 ) + cName + Chr( 0 )
hb_socketSendTo( hSocket, Chr( 6 ) + cName + Chr( 0 ) + iif( cVersion == NIL, "", cVersion ), , , aAddr )
ENDIF
ENDIF
ENDDO
RETURN

View File

@@ -18,6 +18,7 @@ plugins=hbqt_hbmk2_plugin.hbs
{allwin|os2}libpaths=${HB_WITH_QT}\..\lib
{allgcc}libs=supc++
{allgcc&!bsd}libs=supc++
{allgcc&bsd}libs=stdc++
{win|os2}hbcppmm=yes

View File

@@ -1,6 +0,0 @@
#
# $Id$
#
*.prg
-mt

View File

@@ -1,127 +0,0 @@
/*
* $Id$
*/
/*
* This module demonstrates a simple UDP Discovery Server
*
* If you run some service on the network (ex., netio) you need to
* know server IP address and configure client to connect to this
* address. UDPDS helps client to find server address (or addresses
* of multiple servers) on local network. UDPDS should be run in
* parallel to real server (ex., netio). Server part of UDPDS uses
* threads, so, it should be compiled in MT mode.
*
* Server functions:
* UDPDS_Start( nPort, cName [, cVersion ] ) --> hServer
* UDPDS_Stop( hServer )
*
* Client function:
* UDPDS_Find( nPort, cName ) --> { {"ip_addr_1", "version_1"}, ... }
*
*/
#include "hbsocket.ch"
/* Test application */
PROC main( cParam )
LOCAL h
IF ! HB_MTVM()
? "This sample should be compiled using MultiThread"
RETURN
ENDIF
IF cParam == NIL
? "udpds {c|s|cs}"
? "Parameter:"
? " s - run as a server"
? " c - run as a client"
RETURN
ENDIF
IF "S" $ UPPER( cParam )
IF ! EMPTY( h := UDPDS_Start( 39999, "UDPDSDemo", NETNAME() + " " + HB_TSTOSTR(HB_DATETIME() ) ) )
hb_idleSleep( 0.1 )
ENDIF
ENDIF
IF "C" $ UPPER( cParam )
? HB_VALTOEXP( UDPDS_Find( 39999, "UDPDSDemo" ) )
ENDIF
IF "S" $ UPPER( cParam )
? "Press any key to stop server"
INKEY(0)
UDPDS_Stop( h )
ENDIF
RETURN
/* Client */
FUNC UDPDS_Find( nPort, cName )
LOCAL hSocket, aRet, nEnd, nTime, cBuffer, nLen, aAddr
IF ! EMPTY( hSocket := hb_socketOpen( , HB_SOCKET_PT_DGRAM ) )
hb_socketSetBroadcast( hSocket, .T. )
IF hb_socketSendTo( hSocket, CHR( 5 ) + cName + CHR( 0 ),,, { HB_SOCKET_AF_INET, "255.255.255.255", nPort } ) == LEN( cName ) + 2
nTime := hb_milliseconds()
nEnd := nTime + 100 /* 100ms delay is enough on LAN */
aRet := {}
DO WHILE nEnd > nTime
cBuffer := SPACE( 2000 )
nLen := hb_socketRecvFrom( hSocket, @cBuffer,,, @aAddr, nEnd - nTime )
IF LEFT( cBuffer, LEN( cName ) + 2 ) == CHR( 6 ) + cName + CHR( 0 )
AADD( aRet, { aAddr[ 2 ], SUBSTR( cBuffer, LEN( cName ) + 3, nLen - LEN( cName ) - 2 ) } )
ENDIF
nTime := hb_milliseconds()
ENDDO
ENDIF
hb_socketClose( hSocket )
ENDIF
RETURN aRet
/* Server */
FUNC UDPDS_Start( nPort, cName, cVersion )
LOCAL hSocket
IF ! EMPTY( hSocket := hb_socketOpen( , HB_SOCKET_PT_DGRAM ) )
IF hb_socketBind( hSocket, { HB_SOCKET_AF_INET, "0.0.0.0", nPort } )
hb_threadDetach( hb_threadStart( @UDPDS(), hSocket, cName, cVersion ) )
RETURN hSocket
ENDIF
hb_socketClose( hSocket )
ENDIF
RETURN NIL
PROC UDPDS_Stop( hSocket )
hb_socketClose( hSocket )
RETURN
STATIC PROC UDPDS( hSocket, cName, cVersion )
LOCAL cBuffer, nLen, aAddr
DO WHILE .T.
cBuffer := SPACE( 2000 )
nLen := hb_socketRecvFrom( hSocket, @cBuffer,,, @aAddr, 1000 )
IF nLen == -1
IF hb_socketGetError() != HB_SOCKET_ERR_TIMEOUT
RETURN
ENDIF
ELSE
/*
* Communication protocol:
* Broadcast request: ENQ, ServerName, NUL
* Server response: ACK, ServerName, NUL, Version
*/
IF LEFT( cBuffer, nLen ) == CHR( 5 ) + cName + CHR( 0 )
hb_socketSendTo( hSocket, CHR( 6 ) + cName + CHR( 0 ) + IIF( cVersion == NIL, "", cVersion ),,, aAddr )
ENDIF
ENDIF
ENDDO
RETURN

View File

@@ -1157,6 +1157,7 @@ extern HB_EXPORT const char * hb_verHB_COMP( void ); /* retrieves a stat
extern HB_EXPORT HB_BOOL hb_iswin9x( void ); /* return HB_TRUE if OS == Windows 9x, ME */
extern HB_EXPORT HB_BOOL hb_iswinnt( void ); /* return HB_TRUE if OS == Windows NT or newer */
extern HB_EXPORT HB_BOOL hb_iswin2k( void ); /* return HB_TRUE if OS == Windows 2000 or newer */
extern HB_EXPORT HB_BOOL hb_iswin2k3( void ); /* return HB_TRUE if OS == Windows 2003 Server or newer */
extern HB_EXPORT HB_BOOL hb_iswinvista( void ); /* return HB_TRUE if OS == Windows Vista or newer */
extern HB_EXPORT HB_BOOL hb_iswince( void ); /* return HB_TRUE if OS is Windows CE or Windows Mobile */

View File

@@ -470,6 +470,7 @@ char * hb_verPlatform( void )
static HB_BOOL s_fWinVerInit = HB_FALSE;
static HB_BOOL s_fWinVista = HB_FALSE;
static HB_BOOL s_fWin2K3 = HB_FALSE;
static HB_BOOL s_fWin2K = HB_FALSE;
static HB_BOOL s_fWinNT = HB_FALSE;
static HB_BOOL s_fWin9x = HB_FALSE;
@@ -482,9 +483,22 @@ static void s_hb_winVerInit( void )
if( GetVersionEx( &osvi ) )
{
s_fWinVista = osvi.dwMajorVersion >= 6;
s_fWin2K3 = s_fWinVista;
s_fWin2K = osvi.dwMajorVersion >= 5;
s_fWinNT = osvi.dwPlatformId == VER_PLATFORM_WIN32_NT; /* && osvi.dwMajorVersion >= 4); */
s_fWin9x = osvi.dwPlatformId == VER_PLATFORM_WIN32_WINDOWS;
#if !defined( HB_OS_WIN_CE ) && !defined( __DMC__ ) && \
( !defined( _MSC_VER ) || _MSC_VER >= 1400 )
if( ! s_fWin2K3 && osvi.dwMajorVersion == 5 && osvi.dwMinorVersion >= 2 )
{
OSVERSIONINFOEX osVerEx;
osVerEx.dwOSVersionInfoSize = sizeof( osVerEx );
if( GetVersionEx( ( OSVERSIONINFO * ) &osVerEx ) )
s_fWin2K3 = ( osVerEx.wProductType != VER_NT_WORKSTATION );
}
#endif
}
s_fWinVerInit = HB_TRUE;
}
@@ -494,6 +508,7 @@ static void s_hb_winVerInit( void )
static HB_BOOL s_fWinVerInit = HB_FALSE;
static HB_BOOL s_fWinVista = HB_FALSE;
static HB_BOOL s_fWin2K3 = HB_FALSE;
static HB_BOOL s_fWin2K = HB_FALSE;
static HB_BOOL s_fWinNT = HB_FALSE;
static HB_BOOL s_fWin9x = HB_FALSE;
@@ -504,6 +519,7 @@ static void s_hb_winVerInit( void )
/* TODO */
s_fWinVista = HB_FALSE;
s_fWin2K3 = s_fWinVista;
s_fWin2K = HB_FALSE;
/* Host OS detection: Windows NT family */
@@ -545,6 +561,17 @@ HB_BOOL hb_iswinvista( void )
#endif
}
HB_BOOL hb_iswin2k3( void )
{
#if defined( HB_OS_WIN ) || defined( HB_OS_DOS )
if( ! s_fWinVerInit )
s_hb_winVerInit();
return s_fWin2K3;
#else
return HB_FALSE;
#endif
}
HB_BOOL hb_iswin2k( void )
{
#if defined( HB_OS_WIN ) || defined( HB_OS_DOS )

View File

@@ -2432,6 +2432,8 @@ int hb_socketSetNoDelay( HB_SOCKET sd, HB_BOOL fNoDelay )
return ret;
}
/* NOTE: For notes on Windows, see:
http://paste.lisp.org/display/59751 */
int hb_socketSetReuseAddr( HB_SOCKET sd, HB_BOOL fReuse )
{
/* it allows to reuse port immediately without timeout used to