Re: [Libevent-users] Success compile libevent 1.4.3 with VC6
On Wed, Apr 23, 2008 at 07:37:32PM -0400, Nick Mathewson wrote: > On Wed, Apr 23, 2008 at 05:34:04PM +0400, Eugene 'HMage' Bujak wrote: [...] > > * Winsock library needs to be initialized and freed explicitly on win32. > > This is true, but it's not libevent's job to do it. Actually, I think I was wrong here. As James Mansion pointed out, it's okay to call WSAStartup more than once. And given that I just spent 30 minutes trying to track down a bug that was really just forgetting to call WSAStartup() from inside a test in a configure script, I've become pretty sure that it is a useful thing to do. yrs, -- Nick ___ Libevent-users mailing list Libevent-users@monkey.org http://monkeymail.org/mailman/listinfo/libevent-users
Re: [Libevent-users] Success compile libevent 1.4.3 with VC6
On Wed, Apr 23, 2008 at 05:34:04PM +0400, Eugene 'HMage' Bujak wrote: > Hi, > > I want to submit a more complete patch for VC6. > > This one makes all elements of the code compilable and this code is > being used on a production-level project at work. > > The patch is in attachment. Compiles and works under VC6. > * signal_test works. > * timer_test works. > * event_test fails due to the reason that win32 select() can't work on > anything but network sockets. > > Most importantly, my code that runs perfectly well on unix (linux & > freebsd) now runs on windows with little modification. > > But: > * Didn't try to run any other tests since there are no project files for > them. > * Didn't test how mingw32 copes with these changes either. Okay, I've gone through this patch again, under VC++2005. I think my earlier issues still stand, so here's where we are: > The main changes are: > * INPUT and OUTPUT are defined in platform SDK, so I had to redefine > them as EVRPC_INPUT and EVRPC_OUTPUT. See notes in previous patch. > * uint64_t on MSVC must be defined as unsigned __int64 > * int64_t on MSVC is to be defined as signed __int64 Should be fixed. > * MSVC6 doesn't know about __func__ and the #ifdefs weren't guarding > against them good enough. This is just the changes in the sample dir, right? As near as I can tell, the change in config.h shouldn't be necessary, yes? > * winsock2.h sometimes was included after windows.h, that lead to > compiler errors in libevent. Fixed. > * select.c can be painlessly excluded from compilation in win32, but I > still fixed it's compilation. There's no point in including it; it shouldn't be in the win32 project. > * Winsock library needs to be initialized and freed explicitly on win32. Haven't applied yet. > * http.c was using sockaddr_storage. There isn't one in MSVC. Using > sockaddr is good enough for MSVC. Checking for msc isn't right here: newer sdks do indeed seem to define sockaddr_storage. > * There are tons of compiler warnings regarding "do {} while(0);" Sorry, which part fixes this? > * I took the liberty to add #pragma to the WIN32-section of the event.h > so that there's no need to put ws2_32 library into the linker explicitly. > * There's no NFDBITS in msvc. Shouldn't be needed if we don't use the select.c file. > * vsnprintf() is _vsnprintf() for some weird reason on win32. Actually, this underscores a deeper problem. Windows vsnprintf returns -1 if the result is too big for the buffer, but this is not what libevent expects in a lot of places. We need to solve this one. I'm filing a bug here so we don't forget about it. > * I've had to bump tv->tv_usec to 1000 to prevent eating 100% of the cpu > core in win32 dispatch when using timers with events each 10ms or so. Hm? If the timers are happening every 10 ms, then the usec field should be at least 1 already. If there's a small example here to help me wrap my head around the problem, that would be great. > * Also I've provided a gettimeofday() wrapper that uses timeGetTime() > instead of much slower _ftime(). Unfortunately, this will probably turn out to give unreliable results, as it wraps every 49 days. Thus, roughly 1 day out of 50, users' timers will all go off way too early or not at all, depending. Still, it's a shame to use a slow time interface. I hear GetSystemTimeAsFileTime() [or whatever it's called] has a high resolution, but I hear it preforms badly on win9x. Perhaps if we're feeling nutty, we could cobble something monotonic together out of time() and timeGetTime(), like: int fake_gettimeofday(struct timeval *tv, struct timezone *tz) { /* Threadsafety? What threadsafety? Also, not tested. */ static DWORD last_timeGetTime_result = 0; static long seconds_offset = 0; DWORD now = timeGetTime(); time_t seconds = now / 1000; if (!seconds_offset || now < last_timeGetTime_result) { /* Called for the first time, or wrapping around. */ seconds_offset = time(NULL) - seconds; } tv->tv_sec = seconds + seconds_offset; tv->tv_usec = (now % 1000) * 1000; last_timeGetTime_result = now; return 0; } In any case, 1.4.4 will call gettimeofday a lot less frequently than 1.4.3; maybe the ftime() call won't hurt as much now? ___ Libevent-users mailing list Libevent-users@monkey.org http://monkeymail.org/mailman/listinfo/libevent-users
Re: [Libevent-users] Success compile libevent 1.4.3 with VC6
|| -#if defined(_MSC_VER) && _MSC_VER < 1300 || +#ifdef _MSC_VER || #define __func__ "??" | | I thought some versions of VC *did* have an acceptable version of | __func__ or a replacement for it. Yes, __FUNCTION__, as libevent already uses. | What is _MSC_VER defined to on VC6? 1200. _MSC_VER 1200: MSC 12.0, VC 6.0, VS 1998 _MSC_VER 1300: MSC 13.0, VC 7.0, VS 2002 _MSC_VER 1310: MSC 13.1, VC 7.1, VS 2003 _MSC_VER 1400: MSC 14.0, VC 8.0, VS 2005 _MSC_VER 1500: MSC 15.0, VC 9.0, VS 2008 http://predef.sourceforge.net/precomp.html | Should the test be something other than _MSC_VER < 1300? I'm not sure when MSC first added __FUNCTION__ support. It is present in VS2005. The below 'WinCE 5.0 Platform Builder' MSDN excerpt seems to agree with your current (pre-patch) test: snip The new compiler includes the _FUNCTION_ predefined macro. For backward compatible code, add the following definition: #if _MSC_VER < 1300 #define __FUNCTION__ "" #endif snip ___ Libevent-users mailing list Libevent-users@monkey.org http://monkeymail.org/mailman/listinfo/libevent-users
Re: [Libevent-users] Success compile libevent 1.4.3 with VC6
On Sun, Apr 27, 2008 at 02:01:44PM +0100, James Mansion wrote: > > >Also, I think this change will double-initialize winsock on all > >programs that use multiple event bases, and double-shutdown winsock > >whenever the bases are closed on those programs. > > > From the MSDN docs: > > An application can call *WSAStartup* more than once if it needs to > obtain the *WSADATA* structure information more than once. On each such > call, the application can specify any version number supported by the > Winsock DLL. > > An application must call the *WSACleanup* function for every successful > time the *WSAStartup* function is called. Ah! Never mind that part of my message then. If this is so, I see no reason not to add a WSAStartup call. yrs, -- Nick ___ Libevent-users mailing list Libevent-users@monkey.org http://monkeymail.org/mailman/listinfo/libevent-users
Re: [Libevent-users] Success compile libevent 1.4.3 with VC6
Also, I think this change will double-initialize winsock on all programs that use multiple event bases, and double-shutdown winsock whenever the bases are closed on those programs. From the MSDN docs: An application can call *WSAStartup* more than once if it needs to obtain the *WSADATA* structure information more than once. On each such call, the application can specify any version number supported by the Winsock DLL. An application must call the *WSACleanup* function for every successful time the *WSAStartup* function is called. ___ Libevent-users mailing list Libevent-users@monkey.org http://monkeymail.org/mailman/listinfo/libevent-users
Re: [Libevent-users] Success compile libevent 1.4.3 with VC6
On Wed, Apr 23, 2008 at 05:34:04PM +0400, Eugene 'HMage' Bujak wrote: > Hi, > > I want to submit a more complete patch for VC6. > > This one makes all elements of the code compilable and this code is > being used on a production-level project at work. > > The patch is in attachment. Compiles and works under VC6. > * signal_test works. > * timer_test works. > * event_test fails due to the reason that win32 select() can't work on > anything but network sockets. Thanks for the patch; it's good stuff! I'd like to apply it, but there are a few small issues or things that could be done better in order to work well on *non*-vc6 projects. > * INPUT and OUTPUT are defined in platform SDK, so I had to redefine > them as EVRPC_INPUT and EVRPC_OUTPUT. We can't do this change in mainline libevent; it'll break all existing evprc users that use the old names. Maybe there's some way we we can make the old names available on non-vc code, but deprecated in favor of the EVRPC names? something like this: enum EVRPC_HOOK_TYPE { EVRPC_INPUT, EVPRC_OUTPUT, }; #ifndef _WIN32 #define INPUT EVRPC_INPUT #define OUTPUT EVRPC_OUTPUT #endif [...] > * Winsock library needs to be initialized and freed explicitly on win32. This is true, but it's not libevent's job to do it. If we make this change so that libevent starts initializing winsock, we'll break all existing programs that use libevent and know to initialize winsock themselves. It's quite reasonable to call some sockets code before calling event_init, but this part of the patch makes that result in double-initializing winsock. Also, I think this change will double-initialize winsock on all programs that use multiple event bases, and double-shutdown winsock whenever the bases are closed on those programs. [...] > -/* Define to appropriate substitue if compiler doesnt have __func__ */ > -#if defined(_MSC_VER) && _MSC_VER < 1300 > +/* Define to appropriate substitute if compiler doesn't have __func__ */ > +#ifdef _MSC_VER > #define __func__ "??" I thought some versions of VC *did* have an acceptable version of __func__ or a replacement for it. If that's true, this will break those other VCs. What is _MSC_VER defined to on VC6? Should the test be something other than _MSC_VER < 1300? > diff -ur libevent-1.4.3-stable/event-config.h > libevent-1.4.3-stable-win32/event-config.h > --- libevent-1.4.3-stable/event-config.h Wed Apr 23 17:31:14 2008 > +++ libevent-1.4.3-stable-win32/event-config.hWed Apr 23 17:31:01 2008 > @@ -51,7 +51,9 @@ > #define _EVENT_HAVE_INET_NTOP 1 > > /* Define to 1 if you have the header file. */ > +#ifndef _MSC_VER // MSVC doesn't have that > #define _EVENT_HAVE_INTTYPES_H 1 > +#endif This approach is the wrong way to make event-config.h work. On all toolsets besides VC, the file is automatically generated from config.h, which itself is automatically generated by the autoconf script. The right approach for VC is just to have a separate config.h and event-config.h script that work, ideally in the WIN32-Code directory, and set up the compiler's search path so those get used instead of any other ones that might be kicking around. [...] > +#ifdef _WIN32 // MSVC doesn't have that FWIW, many older C compilers don't allow C++-style comments: they weren't added to the C standard till the C99 standard. We need libevent to build on older compilers, so we can't add C++-style comments to libevent. Otherwise, though, this looks like solid work, and I'm quite glad that somebody has a copy of VC6 and the willingness to do it! If you can send in a revised patch, that'd be great. Otherwise, I'll try to hand-apply it with modifications as noted above, but since my x86 box is down at the moment, I can't fire up windows to test it out now, and things might go badly. many thanks, -- Nick Mathewson ___ Libevent-users mailing list Libevent-users@monkey.org http://monkeymail.org/mailman/listinfo/libevent-users
Re: [Libevent-users] Success compile libevent 1.4.3 with VC6
Hi, I want to submit a more complete patch for VC6. This one makes all elements of the code compilable and this code is being used on a production-level project at work. The patch is in attachment. Compiles and works under VC6. * signal_test works. * timer_test works. * event_test fails due to the reason that win32 select() can't work on anything but network sockets. Most importantly, my code that runs perfectly well on unix (linux & freebsd) now runs on windows with little modification. But: * Didn't try to run any other tests since there are no project files for them. * Didn't test how mingw32 copes with these changes either. The main changes are: * INPUT and OUTPUT are defined in platform SDK, so I had to redefine them as EVRPC_INPUT and EVRPC_OUTPUT. * uint64_t on MSVC must be defined as unsigned __int64 * int64_t on MSVC is to be defined as signed __int64 * MSVC6 doesn't know about __func__ and the #ifdefs weren't guarding against them good enough. * winsock2.h sometimes was included after windows.h, that lead to compiler errors in libevent. * select.c can be painlessly excluded from compilation in win32, but I still fixed it's compilation. * Winsock library needs to be initialized and freed explicitly on win32. * http.c was using sockaddr_storage. There isn't one in MSVC. Using sockaddr is good enough for MSVC. * There are tons of compiler warnings regarding "do {} while(0);" * I took the liberty to add #pragma to the WIN32-section of the event.h so that there's no need to put ws2_32 library into the linker explicitly. * There's no NFDBITS in msvc. * vsnprintf() is _vsnprintf() for some weird reason on win32. * I've had to bump tv->tv_usec to 1000 to prevent eating 100% of the cpu core in win32 dispatch when using timers with events each 10ms or so. * Also I've provided a gettimeofday() wrapper that uses timeGetTime() instead of much slower _ftime(). Also, I would like to ask the maintainer of the project to change svn:eol-style property of .dsw and .dsp files on SVN repository toto CRLF, since project loader handles these files properly only when line endings are in windows style. -- - Eugene 'HMage' Bujak. diff -ur libevent-1.4.3-stable/WIN32-Code/config.h libevent-1.4.3-stable-win32/WIN32-Code/config.h --- libevent-1.4.3-stable/WIN32-Code/config.h Wed Apr 23 17:31:16 2008 +++ libevent-1.4.3-stable-win32/WIN32-Code/config.h Wed Apr 23 17:31:03 2008 @@ -205,8 +205,8 @@ /* Version number of package */ #define VERSION "1.3.99-trunk" -/* Define to appropriate substitue if compiler doesnt have __func__ */ -#if defined(_MSC_VER) && _MSC_VER < 1300 +/* Define to appropriate substitute if compiler doesn't have __func__ */ +#ifdef _MSC_VER #define __func__ "??" #else #define __func__ __FUNCTION__ diff -ur libevent-1.4.3-stable/WIN32-Code/misc.c libevent-1.4.3-stable-win32/WIN32-Code/misc.c --- libevent-1.4.3-stable/WIN32-Code/misc.c Wed Apr 23 17:31:16 2008 +++ libevent-1.4.3-stable-win32/WIN32-Code/misc.c Wed Apr 23 17:31:03 2008 @@ -1,9 +1,14 @@ #include #include +#include // winsock2.h must be before windows.h to have any effect #include #include #include +#ifdef _MSC_VER +#pragma comment(lib,"winmm") +#endif + #ifdef __GNUC__ /*our prototypes for timeval and timezone are in here, just in case the above headers don't have them*/ @@ -16,7 +21,7 @@ * * Purpose: Get current time of day. * - * Arguments: tv => Place to store the curent time of day. + * Arguments: tv => Place to store the current time of day. *tz => Ignored. * * Returns: 0 => Success. @@ -24,6 +29,7 @@ / #ifndef HAVE_GETTIMEOFDAY +#ifndef _WIN32 int gettimeofday(struct timeval *tv, struct timezone *tz) { struct _timeb tb; @@ -35,6 +41,21 @@ tv->tv_usec = ((int) tb.millitm) * 1000; return 0; } +#else +struct timezone; +int gettimeofday(struct timeval *tv, struct timezone *tz) { + DWORD ms; + tz; + if(tv == NULL) + return -1; + + ms = timeGetTime(); + tv->tv_sec = ms / 1000;//(long)floor(ms * 0.001); + tv->tv_usec = (ms - (tv->tv_sec*1000))*1000; + + return 0; +} +#endif #endif #if 0 diff -ur libevent-1.4.3-stable/WIN32-Code/win32.c libevent-1.4.3-stable-win32/WIN32-Code/win32.c --- libevent-1.4.3-stable/WIN32-Code/win32.cWed Apr 23 17:31:16 2008 +++ libevent-1.4.3-stable-win32/WIN32-Code/win32.c Wed Apr 23 17:32:04 2008 @@ -32,7 +32,7 @@ #include "../config.h" #endif -#include +#include // winsock2.h must be before windows.h to have any effect #include #include #include @@ -234,6 +234,27 @@ { struct win32op *winop; size_t size; + +#ifdef _WIN32 + WORD wVersionRequested; + WSADATA wsaData; + int retval; + + wVersionRequested = MAKEWORD( 2, 2 ); + + retval = WSAStartup( wVersionRequested, &wsaData ); + if (retval != 0) { +