Initial Windows support. Huge thanks to Vladislav Vaintroub for the patch.
This commit is contained in:
20
README-WIN.txt
Normal file
20
README-WIN.txt
Normal file
@ -0,0 +1,20 @@
|
||||
How to build on Windows
|
||||
|
||||
|
||||
You need CMake (download from http://www.cmake.org/) and Visual Studio 2005 or
|
||||
later (free Express edition should work ok)
|
||||
|
||||
1.Open Visual Studio command line prompt
|
||||
2.To build with MySQL support, you will need mysql.h header file and client
|
||||
library libmysqld.lib
|
||||
One can get them e.g by downloading and unpacking the "zip" distribution of mysql
|
||||
|
||||
- Append directory where libmysql.lib is located to environment variable LIB, e.g
|
||||
set LIB=%LIB%;G:\mysql-noinstall-6.0.6-alpha-win32\mysql-6.0.6-alpha-win32\lib\opt
|
||||
|
||||
- Append directory where mysql.h is located to environment variable INCLUDE, e.g
|
||||
set INCLUDE=%INCLUDE%;G:\mysql-noinstall-6.0.6-alpha-win32\mysql-6.0.6-alpha-win32\include
|
||||
3.In the sysbench directory, execute cmake -G "Visual Studio 9 2008"
|
||||
4.Open sysbench.sln in Explorer and build Relwithdebinfo target.
|
||||
Alternatively, from the command line, issue
|
||||
vcbuild /useenv sysbench.sln "Relwithdebinfo|Win32"
|
||||
109
sysbench/CMakeLists.txt
Normal file
109
sysbench/CMakeLists.txt
Normal file
@ -0,0 +1,109 @@
|
||||
# Copyright (C) 2008 MySQL AB
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; either version 2 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
|
||||
cmake_minimum_required(VERSION 2.6)
|
||||
if(COMMAND cmake_policy)
|
||||
cmake_policy(SET CMP0003 NEW)
|
||||
endif(COMMAND cmake_policy)
|
||||
|
||||
project(sysbench)
|
||||
add_executable(sysbench
|
||||
sysbench.c
|
||||
sysbench.h
|
||||
sb_timer.c
|
||||
sb_timer.h
|
||||
sb_options.c
|
||||
sb_options.h
|
||||
sb_logger.c
|
||||
sb_logger.h
|
||||
sb_list.h
|
||||
db_driver.h
|
||||
db_driver.c
|
||||
sb_win.c
|
||||
sb_win.h
|
||||
)
|
||||
if(MSVC)
|
||||
# Link C runtime statically to avoid hassle with CRT dll redistribution.
|
||||
STRING(REPLACE "/MD" "/MT" CMAKE_C_FLAGS_RELEASE ${CMAKE_C_FLAGS_RELEASE})
|
||||
STRING(REPLACE "/MD" "/MT" CMAKE_C_FLAGS_RELWITHDEBINFO ${CMAKE_C_FLAGS_RELWITHDEBINFO})
|
||||
STRING(REPLACE "/MDd" "/MTd" CMAKE_C_FLAGS_DEBUG ${CMAKE_C_FLAGS_DEBUG})
|
||||
STRING(REPLACE "/MDd" "/MTd" CMAKE_C_FLAGS_DEBUG_INIT ${CMAKE_C_FLAGS_DEBUG_INIT})
|
||||
|
||||
STRING(REPLACE "/MD" "/MT" CMAKE_CXX_FLAGS_RELEASE ${CMAKE_CXX_FLAGS_RELEASE})
|
||||
STRING(REPLACE "/MD" "/MT" CMAKE_CXX_FLAGS_RELWITHDEBINFO ${CMAKE_CXX_FLAGS_RELWITHDEBINFO})
|
||||
STRING(REPLACE "/MDd" "/MTd" CMAKE_CXX_FLAGS_DEBUG ${CMAKE_CXX_FLAGS_DEBUG})
|
||||
STRING(REPLACE "/MDd" "/MTd" CMAKE_CXX_FLAGS_DEBUG_INIT ${CMAKE_CXX_FLAGS_DEBUG_INIT})
|
||||
|
||||
#Silence "deprecated API" warnings.
|
||||
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} /wd4996")
|
||||
|
||||
#Look for mysql.h in INCLUDE paths
|
||||
find_path(MYSQLH_PATH mysql.h ENV INCLUDE)
|
||||
message("mysql.h directory = ${MYSQLH_PATH}")
|
||||
|
||||
#Looks for libmysql.lib in LIB paths
|
||||
find_file(LIBMYSQL_LIB libmysql.lib ENV LIB)
|
||||
message("libmysql.lib = ${LIBMYSQL_LIB}")
|
||||
|
||||
#Look for libmysql.dll
|
||||
find_file(LIBMYSQL_DLL libmysql.dll ENV LIB ENV PATH)
|
||||
message("libmysql.dll = ${LIBMYSQL_DLL}")
|
||||
|
||||
#If mysql header file and client library are found, build with mysql
|
||||
if(MYSQLH_PATH AND LIBMYSQL_LIB)
|
||||
set(USE_MYSQL 1)
|
||||
|
||||
#If libmysql.dll found, copy it next to sysbench.exe in the postbuild step
|
||||
if(LIBMYSQL_DLL)
|
||||
file(TO_NATIVE_PATH ${LIBMYSQL_DLL} LIBMYSQL_DLL)
|
||||
ADD_CUSTOM_COMMAND(
|
||||
TARGET sysbench
|
||||
POST_BUILD
|
||||
COMMAND copy /y ${LIBMYSQL_DLL} $(OutDir)
|
||||
)
|
||||
endif(LIBMYSQL_DLL)
|
||||
endif(MYSQLH_PATH AND LIBMYSQL_LIB)
|
||||
endif(MSVC)
|
||||
|
||||
|
||||
if(USE_MYSQL)
|
||||
message("using mysql driver")
|
||||
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -DUSE_MYSQL")
|
||||
include_directories(${MYSQLH_PATH})
|
||||
add_subdirectory(drivers/mysql)
|
||||
target_link_libraries (sysbench sbmysql)
|
||||
target_link_libraries (sysbench ${LIBMYSQL_LIB})
|
||||
endif(USE_MYSQL)
|
||||
|
||||
add_subdirectory(tests/cpu)
|
||||
target_link_libraries (sysbench sbcpu)
|
||||
|
||||
add_subdirectory(tests/fileio)
|
||||
target_link_libraries (sysbench sbfileio)
|
||||
|
||||
add_subdirectory(tests/mutex)
|
||||
target_link_libraries (sysbench sbmutex)
|
||||
|
||||
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -DHAVE_LUA -DUSE_LUA")
|
||||
add_subdirectory(scripting)
|
||||
target_link_libraries(sysbench sbscript lua)
|
||||
|
||||
|
||||
add_subdirectory(tests/threads)
|
||||
target_link_libraries (sysbench sbthreads)
|
||||
|
||||
add_subdirectory(tests/memory)
|
||||
target_link_libraries (sysbench sbmemory)
|
||||
@ -18,7 +18,9 @@
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include "config.h"
|
||||
#endif
|
||||
|
||||
#ifdef _WIN32
|
||||
#include "sb_win.h"
|
||||
#endif
|
||||
#ifdef STDC_HEADERS
|
||||
# include <ctype.h>
|
||||
#endif
|
||||
@ -681,7 +683,7 @@ void db_free_row(db_row_t *row)
|
||||
int db_bulk_insert_init(db_conn_t *con, const char *query)
|
||||
{
|
||||
drv_caps_t driver_caps;
|
||||
unsigned int query_len;
|
||||
size_t query_len;
|
||||
|
||||
if (con->driver == NULL)
|
||||
return 1;
|
||||
|
||||
2
sysbench/drivers/mysql/CMakeLists.txt
Normal file
2
sysbench/drivers/mysql/CMakeLists.txt
Normal file
@ -0,0 +1,2 @@
|
||||
INCLUDE_DIRECTORIES(${CMAKE_SOURCE_DIR})
|
||||
ADD_LIBRARY(sbmysql drv_mysql.c)
|
||||
@ -21,6 +21,9 @@
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include "config.h"
|
||||
#endif
|
||||
#ifdef _WIN32
|
||||
#include <winsock2.h>
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_STRING_H
|
||||
# include <string.h>
|
||||
@ -117,11 +120,11 @@ db_mysql_bind_map_t db_mysql_bind_map[] =
|
||||
|
||||
static drv_caps_t mysql_drv_caps =
|
||||
{
|
||||
.multi_rows_insert = 1,
|
||||
.prepared_statements = 0,
|
||||
.auto_increment = 1,
|
||||
.serial = 0,
|
||||
.unsigned_int = 1,
|
||||
1,
|
||||
0,
|
||||
1,
|
||||
0,
|
||||
1,
|
||||
};
|
||||
|
||||
|
||||
@ -157,10 +160,9 @@ static int mysql_drv_done(void);
|
||||
|
||||
static db_driver_t mysql_driver =
|
||||
{
|
||||
.sname = "mysql",
|
||||
.lname = "MySQL driver",
|
||||
.args = mysql_drv_args,
|
||||
.ops =
|
||||
"mysql",
|
||||
"MySQL driver",
|
||||
mysql_drv_args,
|
||||
{
|
||||
mysql_drv_init,
|
||||
mysql_drv_describe,
|
||||
@ -179,7 +181,7 @@ static db_driver_t mysql_driver =
|
||||
mysql_drv_store_results,
|
||||
mysql_drv_done
|
||||
},
|
||||
.listitem = {NULL, NULL}
|
||||
{0,0}
|
||||
};
|
||||
|
||||
|
||||
@ -232,6 +234,8 @@ int mysql_drv_init(void)
|
||||
use_ps = 1;
|
||||
#endif
|
||||
|
||||
mysql_library_init(-1, NULL, NULL);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -809,6 +813,8 @@ int mysql_drv_close(db_stmt_t *stmt)
|
||||
/* Uninitialize driver */
|
||||
int mysql_drv_done(void)
|
||||
{
|
||||
mysql_library_end();
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
@ -19,14 +19,16 @@
|
||||
|
||||
#define SB_LIST_H
|
||||
|
||||
typedef struct sb_list_item sb_list_t;
|
||||
typedef struct sb_list_item sb_list_item_t;
|
||||
|
||||
struct sb_list_item
|
||||
typedef struct sb_list_item_t
|
||||
{
|
||||
sb_list_item_t *next_p;
|
||||
sb_list_item_t *prev_p;
|
||||
};
|
||||
// char c;
|
||||
struct sb_list_item_t *next_p;
|
||||
struct sb_list_item_t *prev_p;
|
||||
}
|
||||
sb_list_item_t;
|
||||
|
||||
typedef sb_list_item_t sb_list_item;
|
||||
typedef sb_list_item_t sb_list_t ;
|
||||
|
||||
#ifndef offsetof
|
||||
# define offsetof(type, member) ((size_t) &((type *)0)->member)
|
||||
|
||||
@ -18,6 +18,9 @@
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include "config.h"
|
||||
#endif
|
||||
#ifdef _WIN32
|
||||
#include "sb_win.h"
|
||||
#endif
|
||||
|
||||
#ifdef STDC_HEADERS
|
||||
# include <stdio.h>
|
||||
@ -107,13 +110,13 @@ static sb_arg_t text_handler_args[] =
|
||||
|
||||
|
||||
static log_handler_t text_handler = {
|
||||
.ops = {
|
||||
.init = &text_handler_init,
|
||||
.process = &text_handler_process,
|
||||
.done = NULL,
|
||||
{
|
||||
&text_handler_init,
|
||||
&text_handler_process,
|
||||
NULL,
|
||||
},
|
||||
.args = text_handler_args,
|
||||
.listitem = {NULL, NULL}
|
||||
text_handler_args,
|
||||
{0,0}
|
||||
};
|
||||
|
||||
/* Operation start/stop messages handler */
|
||||
@ -131,13 +134,13 @@ static sb_arg_t oper_handler_args[] =
|
||||
};
|
||||
|
||||
static log_handler_t oper_handler = {
|
||||
.ops = {
|
||||
.init = oper_handler_init,
|
||||
.process = &oper_handler_process,
|
||||
.done = oper_handler_done,
|
||||
{
|
||||
oper_handler_init,
|
||||
&oper_handler_process,
|
||||
oper_handler_done,
|
||||
},
|
||||
.args = oper_handler_args,
|
||||
.listitem = {NULL, NULL}
|
||||
oper_handler_args,
|
||||
{0,0}
|
||||
};
|
||||
|
||||
|
||||
@ -310,19 +313,30 @@ void log_errno(log_msg_priority_t priority, const char *fmt, ...)
|
||||
int n;
|
||||
int old_errno;
|
||||
char *tmp;
|
||||
|
||||
|
||||
#ifdef _WIN32
|
||||
LPVOID lpMsgBuf;
|
||||
old_errno = GetLastError();
|
||||
FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM |
|
||||
FORMAT_MESSAGE_ALLOCATE_BUFFER |
|
||||
FORMAT_MESSAGE_IGNORE_INSERTS,
|
||||
NULL, old_errno,
|
||||
0, (LPTSTR)&lpMsgBuf, 0, NULL);
|
||||
tmp = (char *)lpMsgBuf;
|
||||
#else
|
||||
old_errno = errno;
|
||||
#ifdef HAVE_STRERROR_R
|
||||
#ifdef STRERROR_R_CHAR_P
|
||||
tmp = strerror_r(old_errno, errbuf, ERROR_BUFFER_SIZE);
|
||||
tmp = strerror_r(old_errno, errbuf, sizeof(errbuf));
|
||||
#else
|
||||
strerror_r(old_errno, errbuf, ERROR_BUFFER_SIZE);
|
||||
strerror_r(old_errno, errbuf, sizeof(errbuf));
|
||||
tmp = errbuf;
|
||||
#endif /* STRERROR_R_CHAR_P */
|
||||
#else /* !HAVE_STRERROR_P */
|
||||
strncpy(errbuf, strerror(old_errno), sizeof(errbuf));
|
||||
tmp = errbuf;
|
||||
#endif
|
||||
#endif /* HAVE_STRERROR_P */
|
||||
#endif /* WIN32 */
|
||||
|
||||
va_start(ap, fmt);
|
||||
n = vsnprintf(buf, TEXT_BUFFER_SIZE, fmt, ap);
|
||||
@ -331,6 +345,10 @@ void log_errno(log_msg_priority_t priority, const char *fmt, ...)
|
||||
return;
|
||||
snprintf(buf + n, TEXT_BUFFER_SIZE - n, " errno = %d (%s)", old_errno,
|
||||
tmp);
|
||||
|
||||
#ifdef _WIN32
|
||||
LocalFree(lpMsgBuf);
|
||||
#endif
|
||||
|
||||
log_text(priority, "%s", buf);
|
||||
}
|
||||
@ -406,7 +424,8 @@ int text_handler_process(log_msg_t *msg)
|
||||
}
|
||||
|
||||
printf("%s%s", prefix, text_msg->text);
|
||||
|
||||
fflush(stdout);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
@ -18,6 +18,9 @@
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include "config.h"
|
||||
#endif
|
||||
#ifdef _WIN32
|
||||
# include "sb_win.h"
|
||||
#endif
|
||||
|
||||
#ifdef STDC_HEADERS
|
||||
# include <stdio.h>
|
||||
|
||||
@ -23,9 +23,7 @@
|
||||
#include "config.h"
|
||||
#endif
|
||||
|
||||
#ifdef STDC_HEADERS
|
||||
#include <stdio.h>
|
||||
#endif
|
||||
|
||||
#include "sb_list.h"
|
||||
|
||||
|
||||
@ -22,6 +22,10 @@
|
||||
# include "config.h"
|
||||
#endif
|
||||
|
||||
#ifdef _WIN32
|
||||
#include "sb_win.h"
|
||||
#endif
|
||||
|
||||
#ifdef TIME_WITH_SYS_TIME
|
||||
# include <sys/time.h>
|
||||
# include <time.h>
|
||||
|
||||
244
sysbench/sb_win.c
Normal file
244
sysbench/sb_win.c
Normal file
@ -0,0 +1,244 @@
|
||||
/* Copyright (C) 2008 MySQL AB
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
/*
|
||||
This file contains Windows port of Posix functionality used in sysbench
|
||||
(partial implementation of pthreads, gettimeofday() and random()
|
||||
*/
|
||||
|
||||
#define _CRT_RAND_S /* for rand_s */
|
||||
#include <stdlib.h>
|
||||
#include <windows.h>
|
||||
#include <errno.h>
|
||||
#include "sb_win.h"
|
||||
|
||||
int pthread_cond_init(pthread_cond_t *cond, const pthread_condattr_t *attr)
|
||||
{
|
||||
cond->waiting= 0;
|
||||
InitializeCriticalSection(&cond->lock_waiting);
|
||||
|
||||
cond->events[SIGNAL]= CreateEvent(NULL, FALSE, FALSE, NULL);
|
||||
cond->events[BROADCAST]= CreateEvent(NULL, TRUE, FALSE, NULL);
|
||||
cond->broadcast_block_event= CreateEvent(NULL, TRUE, TRUE, NULL);
|
||||
|
||||
if( cond->events[SIGNAL] == NULL ||
|
||||
cond->events[BROADCAST] == NULL ||
|
||||
cond->broadcast_block_event == NULL )
|
||||
return ENOMEM;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int pthread_cond_destroy(pthread_cond_t *cond)
|
||||
{
|
||||
DeleteCriticalSection(&cond->lock_waiting);
|
||||
|
||||
if (CloseHandle(cond->events[SIGNAL]) == 0 ||
|
||||
CloseHandle(cond->events[BROADCAST]) == 0 ||
|
||||
CloseHandle(cond->broadcast_block_event) == 0)
|
||||
return EINVAL;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
int pthread_cond_wait(pthread_cond_t *cond, pthread_mutex_t *mutex)
|
||||
{
|
||||
return pthread_cond_timedwait(cond,mutex,NULL);
|
||||
}
|
||||
|
||||
|
||||
int pthread_cond_timedwait(pthread_cond_t *cond, pthread_mutex_t *mutex,
|
||||
struct timespec *abstime)
|
||||
{
|
||||
int result;
|
||||
long timeout;
|
||||
union {
|
||||
FILETIME ft;
|
||||
long long i64;
|
||||
}now;
|
||||
|
||||
if( abstime != NULL )
|
||||
{
|
||||
long long stoptime_nanos = (abstime->tv_sec*1000000000 + abstime->tv_nsec);
|
||||
long long now_nanos;
|
||||
long long timeout_nanos;
|
||||
|
||||
GetSystemTimeAsFileTime(&now.ft);
|
||||
now_nanos = now.i64 *100;
|
||||
timeout_nanos = stoptime_nanos - now_nanos;
|
||||
timeout = (long)(timeout_nanos /1000000);
|
||||
}
|
||||
else
|
||||
{
|
||||
/* No time specified; don't expire */
|
||||
timeout= INFINITE;
|
||||
}
|
||||
|
||||
/*
|
||||
Block access if previous broadcast hasn't finished.
|
||||
This is just for safety and should normally not
|
||||
affect the total time spent in this function.
|
||||
*/
|
||||
WaitForSingleObject(cond->broadcast_block_event, INFINITE);
|
||||
|
||||
EnterCriticalSection(&cond->lock_waiting);
|
||||
cond->waiting++;
|
||||
LeaveCriticalSection(&cond->lock_waiting);
|
||||
|
||||
LeaveCriticalSection(mutex);
|
||||
|
||||
result= WaitForMultipleObjects(2, cond->events, FALSE, timeout);
|
||||
|
||||
EnterCriticalSection(&cond->lock_waiting);
|
||||
cond->waiting--;
|
||||
|
||||
if (cond->waiting == 0 && result == (WAIT_OBJECT_0+BROADCAST))
|
||||
{
|
||||
/*
|
||||
We're the last waiter to be notified or to stop waiting, so
|
||||
reset the manual event.
|
||||
*/
|
||||
/* Close broadcast gate */
|
||||
ResetEvent(cond->events[BROADCAST]);
|
||||
/* Open block gate */
|
||||
SetEvent(cond->broadcast_block_event);
|
||||
}
|
||||
LeaveCriticalSection(&cond->lock_waiting);
|
||||
|
||||
EnterCriticalSection(mutex);
|
||||
|
||||
return result == WAIT_TIMEOUT ? ETIMEDOUT : 0;
|
||||
}
|
||||
|
||||
int pthread_cond_signal(pthread_cond_t *cond)
|
||||
{
|
||||
EnterCriticalSection(&cond->lock_waiting);
|
||||
|
||||
if(cond->waiting > 0)
|
||||
SetEvent(cond->events[SIGNAL]);
|
||||
|
||||
LeaveCriticalSection(&cond->lock_waiting);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
int pthread_cond_broadcast(pthread_cond_t *cond)
|
||||
{
|
||||
EnterCriticalSection(&cond->lock_waiting);
|
||||
/*
|
||||
The mutex protect us from broadcasting if
|
||||
there isn't any thread waiting to open the
|
||||
block gate after this call has closed it.
|
||||
*/
|
||||
if(cond->waiting > 0)
|
||||
{
|
||||
/* Close block gate */
|
||||
ResetEvent(cond->broadcast_block_event);
|
||||
/* Open broadcast gate */
|
||||
SetEvent(cond->events[BROADCAST]);
|
||||
}
|
||||
|
||||
LeaveCriticalSection(&cond->lock_waiting);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int pthread_attr_init(pthread_attr_t *attr)
|
||||
{
|
||||
attr->stacksize = 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int pthread_mutex_init(pthread_mutex_t *mutex, const pthread_mutexattr_t *attr)
|
||||
{
|
||||
InitializeCriticalSection(mutex);
|
||||
return 0;
|
||||
}
|
||||
int pthread_mutex_lock(pthread_mutex_t *mutex)
|
||||
{
|
||||
EnterCriticalSection(mutex);
|
||||
return 0;
|
||||
}
|
||||
int pthread_mutex_unlock(pthread_mutex_t *mutex)
|
||||
{
|
||||
LeaveCriticalSection(mutex);
|
||||
return 0;
|
||||
}
|
||||
int pthread_mutex_destroy(pthread_mutex_t *mutex)
|
||||
{
|
||||
DeleteCriticalSection(mutex);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int pthread_create(pthread_t *thread, const pthread_attr_t *attr,
|
||||
void *(*start_routine)(void*), void *arg)
|
||||
{
|
||||
DWORD tid;
|
||||
*thread = CreateThread(NULL, attr->stacksize,
|
||||
(LPTHREAD_START_ROUTINE) start_routine, arg,
|
||||
STACK_SIZE_PARAM_IS_A_RESERVATION, &tid);
|
||||
if (*thread != NULL)
|
||||
return 0;
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Minimal size of thread stack on Windows*/
|
||||
#define PTHREAD_STACK_MIN 65536
|
||||
|
||||
int pthread_attr_setstacksize( pthread_attr_t *attr, size_t stacksize)
|
||||
{
|
||||
if(stacksize)
|
||||
attr->stacksize = max(stacksize, PTHREAD_STACK_MIN);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int pthread_join(pthread_t pthread, void **value_ptr)
|
||||
{
|
||||
if (WaitForSingleObject(pthread, INFINITE) != WAIT_OBJECT_0)
|
||||
return -1;
|
||||
if (value_ptr)
|
||||
*value_ptr = 0;
|
||||
return 0;
|
||||
|
||||
}
|
||||
|
||||
#include <time.h>
|
||||
int gettimeofday(struct timeval * tp, void * tzp)
|
||||
{
|
||||
static long long qpf = 0, startup_time = 0;
|
||||
long long qpc;
|
||||
if(qpf == 0)
|
||||
{
|
||||
QueryPerformanceFrequency((LARGE_INTEGER *)&qpf);
|
||||
}
|
||||
if(startup_time == 0)
|
||||
{
|
||||
QueryPerformanceCounter((LARGE_INTEGER *)&qpc);
|
||||
startup_time = time(NULL) - (qpc/qpf);
|
||||
}
|
||||
QueryPerformanceCounter((LARGE_INTEGER *)&qpc);
|
||||
tp->tv_sec = (long)(startup_time + qpc/qpf);
|
||||
tp->tv_usec = (long)((qpc%qpf)*1000000/qpf);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int random()
|
||||
{
|
||||
int ret;
|
||||
rand_s(&ret);
|
||||
return ret;
|
||||
}
|
||||
103
sysbench/sb_win.h
Normal file
103
sysbench/sb_win.h
Normal file
@ -0,0 +1,103 @@
|
||||
#ifndef SB_WINPORT_H
|
||||
#define SB_WINPORT_H
|
||||
#ifndef _WIN32_WINNT
|
||||
#define _WIN32_WINNT 0x0500
|
||||
#endif
|
||||
#define _CRT_SECURE_NO_WARNINGS
|
||||
#include <windows.h>
|
||||
#include <time.h>
|
||||
#include <string.h>
|
||||
#include <math.h>
|
||||
|
||||
#if (_MSC_VER < 1400)
|
||||
#error "need Visual Studio 2005 or higher"
|
||||
#endif
|
||||
|
||||
#ifndef PACKAGE
|
||||
#define PACKAGE "sysbench"
|
||||
#endif
|
||||
#ifndef PACKAGE_VERSION
|
||||
#define PACKAGE_VERSION "0.5"
|
||||
#endif
|
||||
|
||||
#define snprintf(buffer, count, format,...) \
|
||||
_snprintf_s(buffer,count, _TRUNCATE,format, __VA_ARGS__)
|
||||
#define strcasecmp _stricmp
|
||||
#define strncasecmp _strnicmp
|
||||
#define srandom(seed) srand(seed)
|
||||
typedef intptr_t ssize_t;
|
||||
|
||||
#ifdef _WIN64
|
||||
#define SIZEOF_SIZE_T 8
|
||||
#else
|
||||
#define SIZEOF_SIZE_T 4
|
||||
#endif
|
||||
|
||||
|
||||
struct timespec
|
||||
{
|
||||
time_t tv_sec;
|
||||
long long tv_nsec;
|
||||
};
|
||||
typedef HANDLE pthread_t;
|
||||
typedef CRITICAL_SECTION pthread_mutex_t;
|
||||
|
||||
#define SIGNAL 0
|
||||
#define BROADCAST 1
|
||||
#define MAX_EVENTS 2
|
||||
typedef struct _pthread_cond_t
|
||||
{
|
||||
int waiting;
|
||||
CRITICAL_SECTION lock_waiting;
|
||||
|
||||
HANDLE events[MAX_EVENTS];
|
||||
HANDLE broadcast_block_event;
|
||||
}pthread_cond_t;
|
||||
|
||||
|
||||
typedef struct
|
||||
{
|
||||
char unused;
|
||||
}pthread_condattr_t;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
DWORD stacksize;
|
||||
}pthread_attr_t;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
char unused;
|
||||
}pthread_mutexattr_t;
|
||||
|
||||
extern int pthread_attr_init(pthread_attr_t *attr);
|
||||
extern int pthread_cond_destroy(pthread_cond_t *cond);
|
||||
extern int pthread_cond_init(pthread_cond_t *cond, const pthread_condattr_t *attr);
|
||||
int pthread_cond_timedwait(pthread_cond_t *cond, pthread_mutex_t *mutex,
|
||||
struct timespec *abstime);
|
||||
extern int pthread_cond_wait(pthread_cond_t *cond, pthread_mutex_t *mutex);
|
||||
extern int pthread_cond_signal(pthread_cond_t *cond);
|
||||
extern int pthread_mutex_lock(pthread_mutex_t *mutex);
|
||||
extern int pthread_mutex_unlock(pthread_mutex_t *mutex);
|
||||
extern int pthread_mutex_init(pthread_mutex_t *mutex, const pthread_mutexattr_t *attr);
|
||||
extern int pthread_mutex_destroy(pthread_mutex_t *mutex);
|
||||
extern int pthread_create(pthread_t *thread, const pthread_attr_t *attr, void *(*start_routine)(void*), void *arg);
|
||||
extern int pthread_attr_setstacksize( pthread_attr_t *attr, size_t stacksize);
|
||||
extern int pthread_join(pthread_t thread, void **value_ptr);
|
||||
extern int gettimeofday(struct timeval * tp, void * tzp);
|
||||
extern int random();
|
||||
|
||||
#define ETIMEDOUT 2204
|
||||
|
||||
static __inline int usleep(int micros)
|
||||
{
|
||||
Sleep(micros/1000);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
#define gmtime_r(a,b) gmtime_s(b,a)
|
||||
|
||||
#endif
|
||||
|
||||
20
sysbench/scripting/CMakeLists.txt
Normal file
20
sysbench/scripting/CMakeLists.txt
Normal file
@ -0,0 +1,20 @@
|
||||
# Copyright (C) 2008 MySQL AB
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; either version 2 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
|
||||
include_directories(lua/src ..)
|
||||
add_subdirectory(lua/src)
|
||||
add_library(sbscript sb_script.c sb_script.h script_lua.c script_lua.h)
|
||||
|
||||
27
sysbench/scripting/lua/src/CMakeLists.txt
Normal file
27
sysbench/scripting/lua/src/CMakeLists.txt
Normal file
@ -0,0 +1,27 @@
|
||||
# Copyright (C) 2008 MySQL AB
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; either version 2 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
|
||||
if(MSVC)
|
||||
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -DLUA_WIN")
|
||||
endif(MSVC)
|
||||
add_library(lua lapi.c lcode.c ldebug.c ldo.c ldump.c lfunc.c lgc.c llex.c lmem.c
|
||||
lobject.c lopcodes.c lparser.c lstate.c lstring.c ltable.c ltm.c
|
||||
lundump.c lvm.c lzio.c
|
||||
lauxlib.c lbaselib.c ldblib.c liolib.c lmathlib.c loslib.c ltablib.c
|
||||
lstrlib.c loadlib.c linit.c
|
||||
lapi.h lcode.h ldo.h lgc.h llimits.h lobject.h lparser.h lstring.h ltm.h
|
||||
luaconf.h lundump.h lzio.h lauxlib.h ldebug.h lfunc.h llex.h lmem.h lopcodes.h
|
||||
lstate.h ltable.h lua.h lualib.h lvm.h)
|
||||
@ -32,7 +32,9 @@
|
||||
#define LUA_ANSI
|
||||
#endif
|
||||
|
||||
#ifndef _WIN32
|
||||
#define LUA_USE_DLOPEN
|
||||
#endif
|
||||
|
||||
/*
|
||||
@@ LUA_PATH and LUA_CPATH are the names of the environment variables that
|
||||
|
||||
@ -94,10 +94,16 @@ static int sb_lua_op_thread_done(int);
|
||||
static void sb_lua_op_print_stats(void);
|
||||
|
||||
static sb_operations_t lua_ops = {
|
||||
.init = &sb_lua_init,
|
||||
.get_request = &sb_lua_get_request,
|
||||
.execute_request = &sb_lua_op_execute_request,
|
||||
.done = &sb_lua_done
|
||||
&sb_lua_init,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
&sb_lua_get_request,
|
||||
&sb_lua_op_execute_request,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
&sb_lua_done
|
||||
};
|
||||
|
||||
/* Main (global) interpreter state */
|
||||
@ -240,7 +246,7 @@ int sb_lua_op_execute_request(sb_request_t *sb_req, int thread_id)
|
||||
{
|
||||
log_msg_t msg;
|
||||
log_msg_oper_t op_msg;
|
||||
uint restart;
|
||||
unsigned int restart;
|
||||
lua_State *L = states[thread_id];
|
||||
|
||||
(void)sb_req; /* unused */
|
||||
|
||||
@ -442,7 +442,9 @@ int run_test(sb_test_t *test)
|
||||
|
||||
/* initialize attr */
|
||||
pthread_attr_init(&thread_attr);
|
||||
#ifdef PTHREAD_SCOPE_SYSTEM
|
||||
pthread_attr_setscope(&thread_attr,PTHREAD_SCOPE_SYSTEM);
|
||||
#endif
|
||||
pthread_attr_setstacksize(&thread_attr, thread_stack_size);
|
||||
|
||||
#ifdef HAVE_THR_SETCONCURRENCY
|
||||
@ -468,7 +470,7 @@ int run_test(sb_test_t *test)
|
||||
}
|
||||
pthread_mutex_unlock(&thread_start_mutex);
|
||||
|
||||
log_text(LOG_INFO, "Threads started!");
|
||||
log_text(LOG_NOTICE, "Threads started!\n");
|
||||
for(i = 0; i < sb_globals.num_threads; i++)
|
||||
{
|
||||
if(pthread_join(threads[i].thread, NULL))
|
||||
@ -545,7 +547,7 @@ int init(void)
|
||||
return 1;
|
||||
}
|
||||
|
||||
thread_stack_size = sb_get_value_int("thread-stack-size");
|
||||
thread_stack_size = sb_get_value_size("thread-stack-size");
|
||||
if (thread_stack_size <= 0)
|
||||
{
|
||||
log_text(LOG_FATAL, "Invalid value for thread-stack-size: %d.\n", thread_stack_size);
|
||||
|
||||
2
sysbench/tests/CMakeLists.txt
Normal file
2
sysbench/tests/CMakeLists.txt
Normal file
@ -0,0 +1,2 @@
|
||||
INCLUDE_DIRECTORIES(${CMAKE_SOURCE_DIR})
|
||||
ADD_LIBRARY(sbtests sb_cpu.)
|
||||
18
sysbench/tests/cpu/CMakeLists.txt
Normal file
18
sysbench/tests/cpu/CMakeLists.txt
Normal file
@ -0,0 +1,18 @@
|
||||
# Copyright (C) 2008 MySQL AB
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; either version 2 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
|
||||
INCLUDE_DIRECTORIES(${CMAKE_SOURCE_DIR} ${CMAKE_SOURCE_DIR}/tests)
|
||||
ADD_LIBRARY(sbcpu sb_cpu.c)
|
||||
@ -18,6 +18,9 @@
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include "config.h"
|
||||
#endif
|
||||
#ifdef _WIN32
|
||||
# include "sb_win.h"
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_MATH_H
|
||||
# include <math.h>
|
||||
@ -42,27 +45,24 @@ static int cpu_done(void);
|
||||
|
||||
static sb_test_t cpu_test =
|
||||
{
|
||||
.sname = "cpu",
|
||||
.lname = "CPU performance test",
|
||||
.ops = {
|
||||
.init = cpu_init,
|
||||
.prepare = NULL,
|
||||
.thread_init = NULL,
|
||||
.thread_done = NULL,
|
||||
.cleanup = NULL,
|
||||
.print_mode = cpu_print_mode,
|
||||
.get_request = cpu_get_request,
|
||||
.execute_request = cpu_execute_request,
|
||||
.print_stats = cpu_print_stats,
|
||||
.done = cpu_done
|
||||
"cpu",
|
||||
"CPU performance test",
|
||||
{
|
||||
cpu_init,
|
||||
NULL,
|
||||
NULL,
|
||||
cpu_print_mode,
|
||||
cpu_get_request,
|
||||
cpu_execute_request,
|
||||
cpu_print_stats,
|
||||
NULL,
|
||||
NULL,
|
||||
cpu_done
|
||||
},
|
||||
.cmds = {
|
||||
.prepare = NULL,
|
||||
.help = NULL,
|
||||
.run = NULL,
|
||||
.cleanup = NULL
|
||||
{
|
||||
NULL,NULL,NULL,NULL
|
||||
},
|
||||
.args = cpu_args,
|
||||
cpu_args,
|
||||
{NULL, NULL}
|
||||
};
|
||||
|
||||
|
||||
18
sysbench/tests/fileio/CMakeLists.txt
Normal file
18
sysbench/tests/fileio/CMakeLists.txt
Normal file
@ -0,0 +1,18 @@
|
||||
# Copyright (C) 2008 MySQL AB
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; either version 2 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
|
||||
INCLUDE_DIRECTORIES(${CMAKE_SOURCE_DIR} ${CMAKE_SOURCE_DIR}/tests)
|
||||
ADD_LIBRARY(sbfileio sb_fileio.c crc32.c)
|
||||
@ -26,7 +26,11 @@
|
||||
#define OF(args) args
|
||||
#include "crc32.h"
|
||||
|
||||
#ifndef _WIN32
|
||||
#define ptrdiff_t long
|
||||
#else
|
||||
#include <stdlib.h>
|
||||
#endif
|
||||
|
||||
/* Find a four-byte integer type for crc32_little() and crc32_big(). */
|
||||
#ifndef NOBYFOUR
|
||||
|
||||
@ -19,6 +19,10 @@
|
||||
# include "config.h"
|
||||
#endif
|
||||
|
||||
#ifdef _WIN32
|
||||
#include "sb_win.h"
|
||||
#endif
|
||||
|
||||
#ifdef STDC_HEADERS
|
||||
# include <stdio.h>
|
||||
/* Required for memalign to be declared on Solaris */
|
||||
@ -45,6 +49,14 @@
|
||||
#ifdef HAVE_SYS_MMAN_H
|
||||
# include <sys/mman.h>
|
||||
#endif
|
||||
#ifdef _WIN32
|
||||
# include <io.h>
|
||||
# include <fcntl.h>
|
||||
# include <sys/stat.h>
|
||||
# define S_IRUSR _S_IREAD
|
||||
# define S_IWUSR _S_IWRITE
|
||||
# define HAVE_MMAP
|
||||
#endif
|
||||
|
||||
#include "sysbench.h"
|
||||
#include "crc32.h"
|
||||
@ -53,6 +65,24 @@
|
||||
#define FILE_CHECKSUM_LENGTH sizeof(int)
|
||||
#define FILE_OFFSET_LENGTH sizeof(long)
|
||||
|
||||
#ifdef _WIN32
|
||||
typedef HANDLE FILE_DESCRIPTOR;
|
||||
#define VALID_FILE(fd) (fd != INVALID_HANDLE_VALUE)
|
||||
#define FD_FMT "%p"
|
||||
#define MAP_SHARED 0
|
||||
#define PROT_READ 1
|
||||
#define PROT_WRITE 2
|
||||
#define MAP_FAILED NULL
|
||||
|
||||
void *mmap(void *addr, size_t len, int prot, int flags,
|
||||
FILE_DESCRIPTOR fd, long long off);
|
||||
int munmap(void *addr, size_t size);
|
||||
#else
|
||||
typedef int FILE_DESCRIPTOR;
|
||||
#define VALID_FILE(fd) (fd >= 0)
|
||||
#define FD_FMT "%d"
|
||||
#endif
|
||||
|
||||
/* Supported operations in request */
|
||||
typedef enum
|
||||
{
|
||||
@ -102,8 +132,8 @@ static sb_aio_context_t *aio_ctxts;
|
||||
|
||||
/* Test options */
|
||||
static unsigned int num_files;
|
||||
static off_t total_size;
|
||||
static off_t file_size;
|
||||
static long long total_size;
|
||||
static long long file_size;
|
||||
static int file_block_size;
|
||||
static int file_extra_flags;
|
||||
static int file_fsync_freq;
|
||||
@ -112,7 +142,7 @@ static int file_fsync_end;
|
||||
static file_fsync_mode_t file_fsync_mode;
|
||||
static float file_rw_ratio;
|
||||
static int file_merged_requests;
|
||||
static off_t file_max_request_size;
|
||||
static long long file_max_request_size;
|
||||
static file_io_mode_t file_io_mode;
|
||||
#ifdef HAVE_LIBAIO
|
||||
static unsigned int file_async_backlog;
|
||||
@ -137,12 +167,12 @@ static unsigned long long bytes_written;
|
||||
|
||||
#ifdef HAVE_MMAP
|
||||
/* Array of file mappings */
|
||||
static void **mmaps;
|
||||
static void **mmaps;
|
||||
static unsigned long file_page_mask;
|
||||
#endif
|
||||
|
||||
/* Array of file descriptors */
|
||||
static int *files;
|
||||
static FILE_DESCRIPTOR *files;
|
||||
|
||||
/* Buffer for all I/O operations */
|
||||
static void *buffer;
|
||||
@ -196,33 +226,31 @@ static void file_print_stats(void);
|
||||
|
||||
static sb_test_t fileio_test =
|
||||
{
|
||||
.sname = "fileio",
|
||||
.lname = "File I/O test",
|
||||
.ops =
|
||||
"fileio",
|
||||
"File I/O test",
|
||||
{
|
||||
.init = file_init,
|
||||
.thread_init = NULL,
|
||||
file_init,
|
||||
file_prepare,
|
||||
NULL,
|
||||
file_print_mode,
|
||||
file_get_request,
|
||||
file_execute_request,
|
||||
file_print_stats,
|
||||
#ifdef HAVE_LIBAIO
|
||||
.thread_done = file_thread_done,
|
||||
file_thread_done,
|
||||
#else
|
||||
.thread_done = NULL,
|
||||
NULL,
|
||||
#endif
|
||||
.prepare = file_prepare,
|
||||
.cleanup = NULL,
|
||||
.print_mode = file_print_mode,
|
||||
.get_request = file_get_request,
|
||||
.execute_request = file_execute_request,
|
||||
.print_stats = file_print_stats,
|
||||
.done = file_done
|
||||
file_done
|
||||
},
|
||||
.cmds = {
|
||||
.prepare = file_cmd_prepare,
|
||||
.help = NULL,
|
||||
.run = NULL,
|
||||
.cleanup = file_cmd_cleanup
|
||||
{
|
||||
NULL,
|
||||
file_cmd_prepare,
|
||||
NULL,
|
||||
file_cmd_cleanup
|
||||
},
|
||||
.args = fileio_args,
|
||||
{NULL, NULL}
|
||||
fileio_args,
|
||||
{0,0}
|
||||
};
|
||||
|
||||
|
||||
@ -235,13 +263,13 @@ static sb_request_t file_get_rnd_request(void);
|
||||
static void check_seq_req(sb_file_request_t *, sb_file_request_t *);
|
||||
static const char *get_io_mode_str(file_io_mode_t mode);
|
||||
static const char *get_test_mode_str(file_test_mode_t mode);
|
||||
static void file_fill_buffer(unsigned char *, unsigned int, unsigned long);
|
||||
static int file_validate_buffer(unsigned char *, unsigned int, unsigned long);
|
||||
static void file_fill_buffer(unsigned char *, unsigned int, size_t);
|
||||
static int file_validate_buffer(unsigned char *, unsigned int, size_t);
|
||||
|
||||
/* File operation wrappers */
|
||||
static int file_fsync(unsigned int, int);
|
||||
static ssize_t file_pread(unsigned int, void *, ssize_t, off_t, int);
|
||||
static ssize_t file_pwrite(unsigned int, void *, ssize_t, off_t, int);
|
||||
static ssize_t file_pread(unsigned int, void *, ssize_t, long long, int);
|
||||
static ssize_t file_pwrite(unsigned int, void *, ssize_t, long long, int);
|
||||
#ifdef HAVE_LIBAIO
|
||||
static int file_async_init(void);
|
||||
static int file_async_done(void);
|
||||
@ -255,7 +283,9 @@ static int file_mmap_done(void);
|
||||
|
||||
/* Portability wrappers */
|
||||
static unsigned long sb_getpagesize(void);
|
||||
static unsigned long sb_get_allocation_granularity(void);
|
||||
static void *sb_memalign(size_t size);
|
||||
static void sb_free_memaligned(void *buf);
|
||||
|
||||
int register_test_fileio(sb_list_t *tests)
|
||||
{
|
||||
@ -270,7 +300,7 @@ int file_init(void)
|
||||
if (parse_arguments())
|
||||
return 1;
|
||||
|
||||
files = (int *)malloc(num_files * sizeof(int));
|
||||
files = (FILE_DESCRIPTOR *)malloc(num_files * sizeof(FILE_DESCRIPTOR));
|
||||
if (files == NULL)
|
||||
{
|
||||
log_text(LOG_FATAL, "Memory allocation failure.");
|
||||
@ -301,10 +331,15 @@ int file_prepare(void)
|
||||
unlink(file_name);
|
||||
|
||||
log_text(LOG_DEBUG, "Opening file: %s",file_name);
|
||||
|
||||
#ifndef _WIN32
|
||||
files[i] = open(file_name, O_CREAT | O_RDWR | file_extra_flags,
|
||||
S_IRUSR | S_IWUSR);
|
||||
if (files[i] < 0)
|
||||
#else
|
||||
files[i] = CreateFile(file_name, GENERIC_READ|GENERIC_WRITE, 0, NULL,
|
||||
OPEN_ALWAYS, file_extra_flags? file_extra_flags : FILE_ATTRIBUTE_NORMAL,
|
||||
NULL);
|
||||
#endif
|
||||
if (!VALID_FILE(files[i]))
|
||||
{
|
||||
log_errno(LOG_FATAL, "Cannot open file");
|
||||
return 1;
|
||||
@ -327,7 +362,11 @@ int file_done(void)
|
||||
unsigned int i;
|
||||
|
||||
for (i = 0; i < num_files; i++)
|
||||
#ifndef _WIN32
|
||||
close(files[i]);
|
||||
#else
|
||||
CloseHandle(files[i]);
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_LIBAIO
|
||||
if (file_async_done())
|
||||
@ -340,7 +379,7 @@ int file_done(void)
|
||||
#endif
|
||||
|
||||
if (buffer != NULL)
|
||||
free(buffer);
|
||||
sb_free_memaligned(buffer);
|
||||
|
||||
pthread_mutex_destroy(&fsync_mutex);
|
||||
|
||||
@ -378,7 +417,7 @@ sb_request_t file_get_seq_request(void)
|
||||
if (position + file_max_request_size <= file_size)
|
||||
file_req->size = file_max_request_size;
|
||||
else
|
||||
file_req->size = file_size - position;
|
||||
file_req->size = file_size - position;
|
||||
file_req->file_id = current_file;
|
||||
file_req->pos = position;
|
||||
}
|
||||
@ -445,7 +484,7 @@ sb_request_t file_get_rnd_request(void)
|
||||
{
|
||||
sb_request_t sb_req;
|
||||
sb_file_request_t *file_req = &sb_req.u.file_request;
|
||||
unsigned int rand;
|
||||
unsigned int randnum;
|
||||
unsigned long long tmppos;
|
||||
int real_mode = test_mode;
|
||||
int mode = test_mode;
|
||||
@ -515,16 +554,16 @@ sb_request_t file_get_rnd_request(void)
|
||||
}
|
||||
}
|
||||
|
||||
rand=sb_rnd();
|
||||
randnum=sb_rnd();
|
||||
if (mode==MODE_RND_WRITE) /* mode shall be WRITE or RND_WRITE only */
|
||||
file_req->operation = FILE_OP_TYPE_WRITE;
|
||||
else
|
||||
file_req->operation = FILE_OP_TYPE_READ;
|
||||
|
||||
tmppos = (long long)((double)rand / (double)SB_MAX_RND * (double)(total_size));
|
||||
tmppos = (long long)((double)randnum / (double)SB_MAX_RND * (double)(total_size));
|
||||
tmppos = tmppos - (tmppos % (long long)file_block_size);
|
||||
file_req->file_id = (int)(tmppos / (long long)file_size);
|
||||
file_req->pos = (off_t)(tmppos % (long long)file_size);
|
||||
file_req->pos = (long long)(tmppos % (long long)file_size);
|
||||
file_req->size = file_block_size;
|
||||
|
||||
req_performed++;
|
||||
@ -537,12 +576,11 @@ sb_request_t file_get_rnd_request(void)
|
||||
|
||||
int file_execute_request(sb_request_t *sb_req, int thread_id)
|
||||
{
|
||||
int fd;
|
||||
FILE_DESCRIPTOR fd;
|
||||
sb_file_request_t *file_req = &sb_req->u.file_request;
|
||||
log_msg_t msg;
|
||||
log_msg_oper_t op_msg;
|
||||
|
||||
fd = files[file_req->file_id];
|
||||
|
||||
if (sb_globals.debug)
|
||||
{
|
||||
log_text(LOG_DEBUG,
|
||||
@ -565,7 +603,7 @@ int file_execute_request(sb_request_t *sb_req, int thread_id)
|
||||
log_text(LOG_FATAL, "Too large position discovered in request!");
|
||||
return 1;
|
||||
}
|
||||
|
||||
fd = files[file_req->file_id];
|
||||
/* Prepare log message */
|
||||
msg.type = LOG_MSG_TYPE_OPER;
|
||||
msg.data = &op_msg;
|
||||
@ -585,7 +623,7 @@ int file_execute_request(sb_request_t *sb_req, int thread_id)
|
||||
thread_id)
|
||||
!= (ssize_t)file_req->size)
|
||||
{
|
||||
log_errno(LOG_FATAL, "Failed to write file! file: %d pos: %lld",
|
||||
log_errno(LOG_FATAL, "Failed to write file! file: " FD_FMT " pos: %lld",
|
||||
fd, (long long)file_req->pos);
|
||||
return 1;
|
||||
}
|
||||
@ -595,7 +633,7 @@ int file_execute_request(sb_request_t *sb_req, int thread_id)
|
||||
{
|
||||
if (file_fsync(file_req->file_id, thread_id))
|
||||
{
|
||||
log_errno(LOG_FATAL, "Failed to fsync file! file: %d", fd);
|
||||
log_errno(LOG_FATAL, "Failed to fsync file! file: " FD_FMT, fd);
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
@ -617,7 +655,7 @@ int file_execute_request(sb_request_t *sb_req, int thread_id)
|
||||
thread_id)
|
||||
!= (ssize_t)file_req->size)
|
||||
{
|
||||
log_errno(LOG_FATAL, "Failed to read file! file: %d pos: %lld",
|
||||
log_errno(LOG_FATAL, "Failed to read file! file: " FD_FMT " pos: %lld",
|
||||
fd, (long long)file_req->pos);
|
||||
return 1;
|
||||
}
|
||||
@ -628,8 +666,8 @@ int file_execute_request(sb_request_t *sb_req, int thread_id)
|
||||
file_validate_buffer(buffer, file_req->size, file_req->pos))
|
||||
{
|
||||
log_text(LOG_FATAL,
|
||||
"Validation failed on file %d, block offset 0x%x, exiting...",
|
||||
file_req->file_id, file_req->pos);
|
||||
"Validation failed on file " FD_FMT ", block offset 0x%x, exiting...",
|
||||
file_req->file_id, file_req->pos);
|
||||
return 1;
|
||||
}
|
||||
|
||||
@ -647,7 +685,7 @@ int file_execute_request(sb_request_t *sb_req, int thread_id)
|
||||
break;
|
||||
if(file_fsync(file_req->file_id, thread_id))
|
||||
{
|
||||
log_errno(LOG_FATAL, "Failed to fsync file! file: %d", fd);
|
||||
log_errno(LOG_FATAL, "Failed to fsync file! file: " FD_FMT, fd);
|
||||
return 1;
|
||||
}
|
||||
|
||||
@ -803,7 +841,7 @@ int create_files(void)
|
||||
unsigned int i;
|
||||
int fd;
|
||||
char file_name[512];
|
||||
off_t offset;
|
||||
long long offset;
|
||||
|
||||
log_text(LOG_INFO, "%d files, %ldKb each, %ldMb total", num_files,
|
||||
(long)(file_size / 1024),
|
||||
@ -812,7 +850,6 @@ int create_files(void)
|
||||
for (i=0; i < num_files; i++) {
|
||||
snprintf(file_name, sizeof(file_name), "test_file.%d",i);
|
||||
unlink(file_name);
|
||||
|
||||
fd = open(file_name, O_CREAT | O_WRONLY, S_IRUSR | S_IWUSR);
|
||||
if (fd < 0)
|
||||
{
|
||||
@ -833,7 +870,11 @@ int create_files(void)
|
||||
}
|
||||
|
||||
/* fsync files to prevent cache flush from affecting test results */
|
||||
#ifndef _WIN32
|
||||
fsync(fd);
|
||||
#else
|
||||
_commit(fd);
|
||||
#endif
|
||||
close(fd);
|
||||
}
|
||||
return 0;
|
||||
@ -1111,18 +1152,37 @@ int file_mmap_prepare(void)
|
||||
if (file_io_mode != FILE_IO_MODE_MMAP)
|
||||
return 0;
|
||||
|
||||
file_page_mask = ~(sb_getpagesize() - 1);
|
||||
file_page_mask = ~(sb_get_allocation_granularity() - 1);
|
||||
|
||||
/* Extend file sizes for sequential write test */
|
||||
if (test_mode == MODE_WRITE)
|
||||
for (i = 0; i < num_files; i++)
|
||||
{
|
||||
#ifdef _WIN32
|
||||
HANDLE hFile = files[i];
|
||||
LARGE_INTEGER offset;
|
||||
offset.QuadPart = file_size;
|
||||
if (!SetFilePointerEx(hFile ,offset ,NULL, FILE_BEGIN))
|
||||
{
|
||||
log_errno(LOG_FATAL, "SetFilePointerEx() failed on file %d", i);
|
||||
return 1;
|
||||
}
|
||||
if (!SetEndOfFile(hFile))
|
||||
{
|
||||
log_errno(LOG_FATAL, "SetEndOfFile() failed on file %d", i);
|
||||
return 1;
|
||||
}
|
||||
offset.QuadPart = 0;
|
||||
SetFilePointerEx(hFile ,offset ,NULL, FILE_BEGIN);
|
||||
#else
|
||||
if (ftruncate(files[i], file_size))
|
||||
{
|
||||
log_errno(LOG_FATAL, "ftruncate() failed on file %d", i);
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
||||
#endif
|
||||
}
|
||||
|
||||
#if SIZEOF_SIZE_T > 4
|
||||
mmaps = (void **)malloc(num_files * sizeof(void *));
|
||||
for (i = 0; i < num_files; i++)
|
||||
@ -1168,7 +1228,7 @@ int file_mmap_done(void)
|
||||
|
||||
int file_fsync(unsigned int file_id, int thread_id)
|
||||
{
|
||||
int fd = files[file_id];
|
||||
FILE_DESCRIPTOR fd = files[file_id];
|
||||
#ifdef HAVE_LIBAIO
|
||||
struct iocb iocb;
|
||||
#else
|
||||
@ -1188,7 +1248,11 @@ int file_fsync(unsigned int file_id, int thread_id)
|
||||
)
|
||||
{
|
||||
if (file_fsync_mode == FSYNC_ALL)
|
||||
#ifndef _WIN32
|
||||
return fsync(fd);
|
||||
#else
|
||||
return !FlushFileBuffers(fd);
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_FDATASYNC
|
||||
return fdatasync(fd);
|
||||
@ -1214,22 +1278,128 @@ int file_fsync(unsigned int file_id, int thread_id)
|
||||
/* Use msync on file on 64-bit architectures */
|
||||
else if (file_io_mode == FILE_IO_MODE_MMAP)
|
||||
{
|
||||
#ifndef _WIN32
|
||||
msync(mmaps[file_id], file_size, MS_SYNC | MS_INVALIDATE);
|
||||
#else
|
||||
FlushViewOfFile(mmaps[file_id], (size_t)file_size);
|
||||
#endif
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
return 1; /* Unknown I/O mode */
|
||||
}
|
||||
|
||||
#ifdef _WIN32
|
||||
ssize_t pread(HANDLE hFile, void *buf, ssize_t count, long long offset)
|
||||
{
|
||||
DWORD nBytesRead;
|
||||
OVERLAPPED ov = {0};
|
||||
LARGE_INTEGER li;
|
||||
|
||||
if(!count)
|
||||
return 0;
|
||||
#ifdef _WIN64
|
||||
if(count > UINT_MAX)
|
||||
count= UINT_MAX;
|
||||
#endif
|
||||
|
||||
li.QuadPart = offset;
|
||||
ov.Offset = li.LowPart;
|
||||
ov.OffsetHigh = li.HighPart;
|
||||
|
||||
if(!ReadFile(hFile, buf, (DWORD)count, &nBytesRead, &ov))
|
||||
{
|
||||
DWORD lastError = GetLastError();
|
||||
if(lastError == ERROR_HANDLE_EOF)
|
||||
return 0;
|
||||
return -1;
|
||||
}
|
||||
return nBytesRead;
|
||||
}
|
||||
ssize_t pwrite(HANDLE hFile, const void *buf, size_t count,
|
||||
long long offset)
|
||||
{
|
||||
DWORD nBytesWritten;
|
||||
OVERLAPPED ov = {0};
|
||||
LARGE_INTEGER li;
|
||||
|
||||
if(!count)
|
||||
return 0;
|
||||
|
||||
#ifdef _WIN64
|
||||
if(count > UINT_MAX)
|
||||
count= UINT_MAX;
|
||||
#endif
|
||||
|
||||
li.QuadPart = offset;
|
||||
ov.Offset = li.LowPart;
|
||||
ov.OffsetHigh= li.HighPart;
|
||||
|
||||
if(!WriteFile(hFile, buf, (DWORD)count, &nBytesWritten, &ov))
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
else
|
||||
return nBytesWritten;
|
||||
}
|
||||
|
||||
#define MAP_SHARED 0
|
||||
#define PROT_READ 1
|
||||
#define PROT_WRITE 2
|
||||
#define MAP_FAILED NULL
|
||||
|
||||
void *mmap(void *addr, size_t len, int prot, int flags,
|
||||
FILE_DESCRIPTOR fd, long long off)
|
||||
{
|
||||
DWORD flProtect;
|
||||
DWORD flMap;
|
||||
void *retval;
|
||||
LARGE_INTEGER li;
|
||||
HANDLE hMap;
|
||||
|
||||
switch(prot)
|
||||
{
|
||||
case PROT_READ:
|
||||
flProtect = PAGE_READONLY;
|
||||
flMap = FILE_MAP_READ;
|
||||
break;
|
||||
case PROT_READ|PROT_WRITE:
|
||||
flProtect = PAGE_READWRITE;
|
||||
flMap = FILE_MAP_ALL_ACCESS;
|
||||
break;
|
||||
default:
|
||||
return MAP_FAILED;
|
||||
}
|
||||
hMap = CreateFileMapping(fd, NULL, flProtect, 0 , 0, NULL);
|
||||
|
||||
if(hMap == INVALID_HANDLE_VALUE)
|
||||
return MAP_FAILED;
|
||||
|
||||
li.QuadPart = off;
|
||||
retval = MapViewOfFileEx(hMap, flMap, li.HighPart, li.LowPart, len, NULL);
|
||||
|
||||
CloseHandle(hMap);
|
||||
return retval;
|
||||
}
|
||||
|
||||
int munmap(void *start, size_t len)
|
||||
{
|
||||
(void) len; /* unused */
|
||||
if(UnmapViewOfFile(start))
|
||||
return 0;
|
||||
return -1;
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
ssize_t file_pread(unsigned int file_id, void *buf, ssize_t count,
|
||||
off_t offset, int thread_id)
|
||||
long long offset, int thread_id)
|
||||
{
|
||||
int fd = files[file_id];
|
||||
FILE_DESCRIPTOR fd = files[file_id];
|
||||
#ifdef HAVE_MMAP
|
||||
void *start;
|
||||
off_t page_addr;
|
||||
off_t page_offset;
|
||||
long long page_addr;
|
||||
long long page_offset;
|
||||
#endif
|
||||
#ifdef HAVE_LIBAIO
|
||||
struct iocb iocb;
|
||||
@ -1264,7 +1434,6 @@ ssize_t file_pread(unsigned int file_id, void *buf, ssize_t count,
|
||||
return 0;
|
||||
memcpy(buffer, (char *)start + page_offset, count);
|
||||
munmap(start, count + page_offset);
|
||||
|
||||
return count;
|
||||
# else
|
||||
(void)start; /* unused */
|
||||
@ -1284,9 +1453,9 @@ ssize_t file_pread(unsigned int file_id, void *buf, ssize_t count,
|
||||
|
||||
|
||||
ssize_t file_pwrite(unsigned int file_id, void *buf, ssize_t count,
|
||||
off_t offset, int thread_id)
|
||||
long long offset, int thread_id)
|
||||
{
|
||||
int fd = files[file_id];
|
||||
FILE_DESCRIPTOR fd = files[file_id];
|
||||
#ifdef HAVE_MMAP
|
||||
void *start;
|
||||
size_t page_addr;
|
||||
@ -1321,6 +1490,7 @@ ssize_t file_pwrite(unsigned int file_id, void *buf, ssize_t count,
|
||||
page_offset = offset - page_addr;
|
||||
start = mmap(NULL, count + page_offset, PROT_READ | PROT_WRITE, MAP_SHARED,
|
||||
fd, page_addr);
|
||||
|
||||
if (start == MAP_FAILED)
|
||||
return 0;
|
||||
memcpy((char *)start + page_offset, buffer, count);
|
||||
@ -1453,7 +1623,13 @@ int parse_arguments(void)
|
||||
if (mode == NULL || !strlen(mode))
|
||||
file_extra_flags = 0;
|
||||
else if (!strcmp(mode, "sync"))
|
||||
{
|
||||
#ifdef _WIN32
|
||||
file_extra_flags = FILE_FLAG_WRITE_THROUGH;
|
||||
#else
|
||||
file_extra_flags = O_SYNC;
|
||||
#endif
|
||||
}
|
||||
else if (!strcmp(mode, "dsync"))
|
||||
{
|
||||
#ifdef O_DSYNC
|
||||
@ -1465,7 +1641,9 @@ int parse_arguments(void)
|
||||
}
|
||||
else if (!strcmp(mode, "direct"))
|
||||
{
|
||||
#ifdef O_DIRECT
|
||||
#ifdef _WIN32
|
||||
file_extra_flags = FILE_FLAG_NO_BUFFERING;
|
||||
#elif defined(O_DIRECT)
|
||||
file_extra_flags = O_DIRECT;
|
||||
#else
|
||||
log_text(LOG_FATAL, "O_DIRECT is not supported on this platform.");
|
||||
@ -1572,15 +1750,34 @@ unsigned long sb_getpagesize(void)
|
||||
{
|
||||
#ifdef _SC_PAGESIZE
|
||||
return sysconf(_SC_PAGESIZE);
|
||||
#elif defined _WIN32
|
||||
SYSTEM_INFO info;
|
||||
GetSystemInfo(&info);
|
||||
return info.dwPageSize;
|
||||
#else
|
||||
return getpagesize();
|
||||
#endif
|
||||
}
|
||||
|
||||
/*
|
||||
Alignment requirement for mmap(). The same as page size, except on Windows
|
||||
(on Windows it has to be 64KB, even if pagesize is only 4 or 8KB)
|
||||
*/
|
||||
unsigned long sb_get_allocation_granularity(void)
|
||||
{
|
||||
#ifdef _WIN32
|
||||
SYSTEM_INFO info;
|
||||
GetSystemInfo(&info);
|
||||
return info.dwAllocationGranularity;
|
||||
#else
|
||||
return sb_getpagesize();
|
||||
#endif
|
||||
}
|
||||
|
||||
/* Allocate a buffer of a specified size and align it to the page size */
|
||||
|
||||
|
||||
/*
|
||||
Allocate a buffer of a specified size and align it to the allocation
|
||||
granularity
|
||||
*/
|
||||
void *sb_memalign(size_t size)
|
||||
{
|
||||
unsigned long page_size;
|
||||
@ -1595,6 +1792,9 @@ void *sb_memalign(size_t size)
|
||||
#elif defined(HAVE_VALLOC)
|
||||
(void)page_size; /* unused */
|
||||
buffer = valloc(size);
|
||||
#elif defined (_WIN32)
|
||||
(void)page_size; /* unused */
|
||||
buffer = VirtualAlloc(NULL, size, MEM_RESERVE|MEM_COMMIT, PAGE_READWRITE);
|
||||
#else
|
||||
(void)page_size; /* unused */
|
||||
log_text(LOG_WARNING, "None of valloc(), memalign and posix_memalign() is available, doing unaligned IO!");
|
||||
@ -1604,12 +1804,20 @@ void *sb_memalign(size_t size)
|
||||
return buffer;
|
||||
}
|
||||
|
||||
static void sb_free_memaligned(void *buf)
|
||||
{
|
||||
#ifdef _WIN32
|
||||
VirtualFree(buf,0,MEM_FREE);
|
||||
#else
|
||||
free(buf);
|
||||
#endif
|
||||
}
|
||||
|
||||
/* Fill buffer with random values and write checksum */
|
||||
|
||||
|
||||
void file_fill_buffer(unsigned char *buf, unsigned int len,
|
||||
unsigned long offset)
|
||||
size_t offset)
|
||||
{
|
||||
unsigned int i;
|
||||
|
||||
@ -1627,7 +1835,7 @@ void file_fill_buffer(unsigned char *buf, unsigned int len,
|
||||
/* Validate checksum and offset of block read from disk */
|
||||
|
||||
|
||||
int file_validate_buffer(unsigned char *buf, unsigned int len, unsigned long offset)
|
||||
int file_validate_buffer(unsigned char *buf, unsigned int len, size_t offset)
|
||||
{
|
||||
unsigned int checksum;
|
||||
unsigned int cs_offset;
|
||||
@ -1644,11 +1852,11 @@ int file_validate_buffer(unsigned char *buf, unsigned int len, unsigned long of
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (offset != *(unsigned long *)(buf + cs_offset + FILE_CHECKSUM_LENGTH))
|
||||
if (offset != *(size_t *)(buf + cs_offset + FILE_CHECKSUM_LENGTH))
|
||||
{
|
||||
log_text(LOG_FATAL, "Offset mismatch in block:");
|
||||
log_text(LOG_FATAL, " Actual offset: %ld Stored offset: %ld",
|
||||
offset, *(unsigned long *)(buf + cs_offset + FILE_CHECKSUM_LENGTH));
|
||||
offset, *(size_t *)(buf + cs_offset + FILE_CHECKSUM_LENGTH));
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
||||
18
sysbench/tests/memory/CMakeLists.txt
Normal file
18
sysbench/tests/memory/CMakeLists.txt
Normal file
@ -0,0 +1,18 @@
|
||||
# Copyright (C) 2008 MySQL AB
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; either version 2 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
|
||||
include_directories(${CMAKE_SOURCE_DIR} ${CMAKE_SOURCE_DIR}/tests)
|
||||
add_library(sbmemory sb_memory.c)
|
||||
@ -18,6 +18,9 @@
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include "config.h"
|
||||
#endif
|
||||
#ifdef _WIN32
|
||||
#include "sb_win.h"
|
||||
#endif
|
||||
|
||||
#include "sysbench.h"
|
||||
|
||||
@ -58,35 +61,34 @@ static void memory_print_stats(void);
|
||||
|
||||
static sb_test_t memory_test =
|
||||
{
|
||||
.sname = "memory",
|
||||
.lname = "Memory functions speed test",
|
||||
.ops =
|
||||
"memory",
|
||||
"Memory functions speed test",
|
||||
{
|
||||
.init = memory_init,
|
||||
.prepare = NULL,
|
||||
.thread_init = NULL,
|
||||
.thread_done = NULL,
|
||||
.cleanup = NULL,
|
||||
.print_mode = memory_print_mode,
|
||||
.get_request = memory_get_request,
|
||||
.execute_request = memory_execute_request,
|
||||
.print_stats = memory_print_stats,
|
||||
.done = NULL
|
||||
memory_init,
|
||||
NULL,
|
||||
NULL,
|
||||
memory_print_mode,
|
||||
memory_get_request,
|
||||
memory_execute_request,
|
||||
memory_print_stats,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL
|
||||
},
|
||||
.cmds = {
|
||||
.help = NULL,
|
||||
.prepare = NULL,
|
||||
.run = NULL,
|
||||
.cleanup = NULL
|
||||
{
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL
|
||||
},
|
||||
.args = memory_args,
|
||||
memory_args,
|
||||
{NULL, NULL}
|
||||
};
|
||||
|
||||
/* Test arguments */
|
||||
|
||||
static ssize_t memory_block_size;
|
||||
static off_t memory_total_size;
|
||||
static size_t memory_total_size;
|
||||
static unsigned int memory_scope;
|
||||
static unsigned int memory_oper;
|
||||
static unsigned int memory_access_rnd;
|
||||
@ -96,7 +98,7 @@ static unsigned int memory_hugetlb;
|
||||
|
||||
/* Statistics */
|
||||
static unsigned int total_ops;
|
||||
static off_t total_bytes;
|
||||
static size_t total_bytes;
|
||||
|
||||
/* Array of per-thread buffers */
|
||||
static int **buffers;
|
||||
|
||||
18
sysbench/tests/mutex/CMakeLists.txt
Normal file
18
sysbench/tests/mutex/CMakeLists.txt
Normal file
@ -0,0 +1,18 @@
|
||||
# Copyright (C) 2008 MySQL AB
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; either version 2 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
|
||||
include_directories(${CMAKE_SOURCE_DIR} ${CMAKE_SOURCE_DIR}/tests)
|
||||
add_library(sbmutex sb_mutex.c)
|
||||
@ -19,6 +19,10 @@
|
||||
# include "config.h"
|
||||
#endif
|
||||
|
||||
#ifdef _WIN32
|
||||
# include "sb_win.h"
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_PTHREAD_H
|
||||
# include <pthread.h>
|
||||
#endif
|
||||
@ -52,27 +56,26 @@ static int mutex_done(void);
|
||||
|
||||
static sb_test_t mutex_test =
|
||||
{
|
||||
.sname = "mutex",
|
||||
.lname = "Mutex performance test",
|
||||
.ops = {
|
||||
.init = mutex_init,
|
||||
.prepare = NULL,
|
||||
.thread_init = NULL,
|
||||
.thread_done = NULL,
|
||||
.print_mode = mutex_print_mode,
|
||||
.print_stats = NULL,
|
||||
.get_request = mutex_get_request,
|
||||
.execute_request = mutex_execute_request,
|
||||
.cleanup = NULL,
|
||||
.done = mutex_done
|
||||
"mutex",
|
||||
"Mutex performance test",
|
||||
{
|
||||
mutex_init,
|
||||
NULL,
|
||||
NULL,
|
||||
mutex_print_mode,
|
||||
mutex_get_request,
|
||||
mutex_execute_request,
|
||||
NULL,
|
||||
NULL,
|
||||
mutex_done
|
||||
},
|
||||
.cmds = {
|
||||
.help = NULL,
|
||||
.prepare = NULL,
|
||||
.run = NULL,
|
||||
.cleanup = NULL
|
||||
{
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL
|
||||
},
|
||||
.args = mutex_args,
|
||||
mutex_args,
|
||||
{NULL, NULL}
|
||||
};
|
||||
|
||||
@ -141,7 +144,7 @@ sb_request_t mutex_get_request(void)
|
||||
int mutex_execute_request(sb_request_t *sb_req, int thread_id)
|
||||
{
|
||||
unsigned int i;
|
||||
unsigned int c;
|
||||
unsigned int c=0;
|
||||
unsigned int current_lock;
|
||||
sb_mutex_request_t *mutex_req = &sb_req->u.mutex_request;
|
||||
log_msg_t msg;
|
||||
|
||||
@ -18,6 +18,10 @@
|
||||
#ifndef SB_FILEIO_H
|
||||
#define SB_FILEIO_H
|
||||
|
||||
#ifdef _WIN32
|
||||
#include "sb_win.h" /* ssize_t defined*/
|
||||
#endif
|
||||
|
||||
/* File operation types */
|
||||
typedef enum
|
||||
{
|
||||
@ -32,7 +36,7 @@ typedef enum
|
||||
typedef struct
|
||||
{
|
||||
unsigned int file_id;
|
||||
off_t pos;
|
||||
long long pos;
|
||||
ssize_t size;
|
||||
sb_file_op_t operation;
|
||||
} sb_file_request_t;
|
||||
|
||||
@ -40,7 +40,7 @@ typedef enum
|
||||
typedef struct
|
||||
{
|
||||
sb_mem_op_t type;
|
||||
unsigned long block_size;
|
||||
size_t block_size;
|
||||
sb_mem_scope_t scope;
|
||||
} sb_mem_request_t;
|
||||
|
||||
|
||||
18
sysbench/tests/threads/CMakeLists.txt
Normal file
18
sysbench/tests/threads/CMakeLists.txt
Normal file
@ -0,0 +1,18 @@
|
||||
# Copyright (C) 2008 MySQL AB
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; either version 2 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
|
||||
include_directories(${CMAKE_SOURCE_DIR} ${CMAKE_SOURCE_DIR}/tests)
|
||||
add_library(sbthreads sb_threads.c)
|
||||
@ -19,6 +19,10 @@
|
||||
# include "config.h"
|
||||
#endif
|
||||
|
||||
#ifdef _WIN32
|
||||
# include "sb_win.h"
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_PTHREAD_H
|
||||
# include <pthread.h>
|
||||
#endif
|
||||
@ -28,6 +32,8 @@
|
||||
/* How to test scheduler pthread_yield or sched_yield */
|
||||
#ifdef HAVE_PTHREAD_YIELD
|
||||
#define YIELD pthread_yield
|
||||
#elif defined (_WIN32)
|
||||
#define YIELD SwitchToThread
|
||||
#else
|
||||
#define YIELD sched_yield
|
||||
#endif
|
||||
@ -53,27 +59,27 @@ static int threads_cleanup(void);
|
||||
|
||||
static sb_test_t threads_test =
|
||||
{
|
||||
.sname = "threads",
|
||||
.lname = "Threads subsystem performance test",
|
||||
.ops = {
|
||||
.init = threads_init,
|
||||
.prepare = threads_prepare,
|
||||
.thread_init = NULL,
|
||||
.thread_done = NULL,
|
||||
.print_mode = threads_print_mode,
|
||||
.print_stats = NULL,
|
||||
.get_request = threads_get_request,
|
||||
.execute_request = threads_execute_request,
|
||||
.cleanup = threads_cleanup,
|
||||
.done = NULL
|
||||
"threads",
|
||||
"Threads subsystem performance test",
|
||||
{
|
||||
threads_init,
|
||||
threads_prepare,
|
||||
NULL,
|
||||
threads_print_mode,
|
||||
threads_get_request,
|
||||
threads_execute_request,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
threads_cleanup,
|
||||
},
|
||||
.cmds = {
|
||||
.help = NULL,
|
||||
.prepare = NULL,
|
||||
.run = NULL,
|
||||
.cleanup = NULL
|
||||
{
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL
|
||||
},
|
||||
.args = threads_args,
|
||||
threads_args,
|
||||
{NULL, NULL}
|
||||
};
|
||||
|
||||
|
||||
Reference in New Issue
Block a user