#include <errno.h>
#include <string.h>
-#ifdef HAVE_UNISTD_H
+#if defined(HAVE_UNISTD_H)
#include <unistd.h>
#include <fcntl.h>
+#elif defined(HOST_WIN32)
+#include <windows.h>
#endif
-/* FIXME Implement binary protocol IO on systems that don't have unistd */
-#ifdef HAVE_UNISTD_H
+#if defined(HOST_WIN32)
+static const HANDLE invalid_file_value = INVALID_HANDLE_VALUE;
/* If valid, dump binary protocol to this file */
+static HANDLE binary_protocol_file = INVALID_HANDLE_VALUE;
+#else
+static const int invalid_file_value = -1;
static int binary_protocol_file = -1;
+#endif
/* We set this to -1 to indicate an exclusive lock */
static volatile int binary_protocol_use_count = 0;
else
filename = filename_or_prefix;
+#if defined(HAVE_UNISTD_H)
do {
binary_protocol_file = open (filename, O_CREAT | O_WRONLY, 0644);
if (binary_protocol_file == -1) {
ftruncate (binary_protocol_file, 0);
}
} while (binary_protocol_file == -1);
+#elif defined(HOST_WIN32)
+ binary_protocol_file = CreateFileA (filename, GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
+#else
+ g_error ("sgen binary protocol: not supported");
+#endif
- if (binary_protocol_file == -1 && assert_on_failure)
+ if (binary_protocol_file == invalid_file_value && assert_on_failure)
g_error ("sgen binary protocol: failed to open file");
if (file_size_limit > 0)
free_filename (filename);
}
-#endif
void
binary_protocol_init (const char *filename, long long limit)
{
-#ifdef HAVE_UNISTD_H
file_size_limit = limit;
/* Original name length + . + pid length in hex + null terminator */
filename_or_prefix = g_strdup_printf ("%s", filename);
binary_protocol_open_file (FALSE);
- if (binary_protocol_file == -1) {
+ if (binary_protocol_file == invalid_file_value) {
/* Another process owns the file, try adding the pid suffix to the filename */
gint32 pid = mono_process_current_pid ();
g_free (filename_or_prefix);
g_free (filename_or_prefix);
binary_protocol_header (PROTOCOL_HEADER_CHECK, PROTOCOL_HEADER_VERSION, SIZEOF_VOID_P, G_BYTE_ORDER == G_LITTLE_ENDIAN);
-#else
- g_error ("sgen binary protocol: not supported");
-#endif
}
gboolean
binary_protocol_is_enabled (void)
{
-#ifdef HAVE_UNISTD_H
- return binary_protocol_file != -1;
-#else
- return FALSE;
-#endif
+ return binary_protocol_file != invalid_file_value;
}
-#ifdef HAVE_UNISTD_H
-
static void
close_binary_protocol_file (void)
{
+#if defined(HAVE_UNISTD_H)
while (close (binary_protocol_file) == -1 && errno == EINTR)
;
- binary_protocol_file = -1;
+#elif defined(HOST_WIN32)
+ CloseHandle (binary_protocol_file);
+#endif
+ binary_protocol_file = invalid_file_value;
}
static gboolean
g_assert (buffer->index > 0);
while (written < to_write) {
+#if defined(HAVE_UNISTD_H)
ret = write (binary_protocol_file, buffer->buffer + written, to_write - written);
if (ret >= 0)
written += ret;
continue;
else
close_binary_protocol_file ();
+#elif defined(HOST_WIN32)
+ int tmp_written;
+ if (WriteFile (binary_protocol_file, buffer->buffer + written, to_write - written, &tmp_written, NULL))
+ written += tmp_written;
+ else
+ close_binary_protocol_file ();
+#endif
}
current_file_size += buffer->index;
binary_protocol_open_file (TRUE);
}
-#endif
/*
* Flushing buffers takes an exclusive lock, so it must only be done when the world is
gboolean
binary_protocol_flush_buffers (gboolean force)
{
-#ifdef HAVE_UNISTD_H
int num_buffers = 0, i;
BinaryProtocolBuffer *header;
BinaryProtocolBuffer *buf;
BinaryProtocolBuffer **bufs;
- if (binary_protocol_file == -1)
+ if (binary_protocol_file == invalid_file_value)
return FALSE;
if (!force && !try_lock_exclusive ())
unlock_exclusive ();
return TRUE;
-#endif
}
-#ifdef HAVE_UNISTD_H
static BinaryProtocolBuffer*
binary_protocol_get_buffer (int length)
{
return new_buffer;
}
-#endif
static void
protocol_entry (unsigned char type, gpointer data, int size)
{
-#ifdef HAVE_UNISTD_H
int index;
BinaryProtocolBuffer *buffer;
- if (binary_protocol_file == -1)
+ if (binary_protocol_file == invalid_file_value)
return;
if (sgen_thread_pool_is_thread_pool_thread (mono_native_thread_id_get ()))
g_assert (index <= BINARY_PROTOCOL_BUFFER_SIZE);
unlock_recursive ();
-#endif
}
#define TYPE_INT int
#define BINARY_PROTOCOL_NO_MATCH (-1)
#define BINARY_PROTOCOL_MATCH (-2)
-/* We pack all protocol structs by default unless specified otherwise */
-#ifndef PROTOCOL_STRUCT_ATTR
-#ifdef __GNUC__
-#define PROTOCOL_STRUCT_ATTR __attribute__ ((packed))
-#else
-#define PROTOCOL_STRUCT_ATTR
-#endif
-#endif
-
#define PROTOCOL_ID(method) method ## _id
#define PROTOCOL_STRUCT(method) method ## _struct
#define CLIENT_PROTOCOL_NAME(method) sgen_client_ ## method
#include "sgen-protocol-def.h"
};
+/* We pack all protocol structs by default unless specified otherwise */
+#ifndef PROTOCOL_STRUCT_ATTR
+
+#define PROTOCOL_PACK_STRUCTS
+
+#if defined(__GNUC__)
+#define PROTOCOL_STRUCT_ATTR __attribute__ ((packed))
+#else
+#define PROTOCOL_STRUCT_ATTR
+#endif
+
+#endif
+
#define BEGIN_PROTOCOL_ENTRY0(method)
#define BEGIN_PROTOCOL_ENTRY1(method,t1,f1) \
typedef struct PROTOCOL_STRUCT_ATTR { \
#define END_PROTOCOL_ENTRY_FLUSH
#define END_PROTOCOL_ENTRY_HEAVY
+#if defined(_MSC_VER) && defined(PROTOCOL_PACK_STRUCTS)
+#pragma pack(push)
+#pragma pack(1)
+#endif
#include "sgen-protocol-def.h"
+#if defined(_MSC_VER) && defined(PROTOCOL_PACK_STRUCTS)
+#pragma pack(pop)
+#undef PROTOCOL_PACK_STRUCTS
+#endif
/* missing: finalizers, roots, non-store wbarriers */