Browse Source

Merge branch 'develop' into x64

Conflicts:
	cmake/EthDependencies.cmake
cl-refactor
Marek Kotewicz 10 years ago
parent
commit
08a86a2b85
  1. 19
      CMakeLists.txt
  2. 161
      cmake/CMakeParseArguments.cmake
  3. 16
      cmake/EthDependencies.cmake
  4. 33
      cmake/FindCpuid.cmake
  5. 136
      cmake/FindOpenCL.cmake
  6. 382
      cmake/FindPackageHandleStandardArgs.cmake
  7. 57
      cmake/FindPackageMessage.cmake
  8. 1
      eth/CMakeLists.txt
  9. 192
      eth/main.cpp
  10. 48
      libethash-cl/CMakeLists.txt
  11. 38
      libethash-cl/ethash_cl_miner.cpp
  12. 12
      libethash-cl/ethash_cl_miner.h
  13. 8
      libethcore/CMakeLists.txt
  14. 66
      libethcore/Ethash.cpp
  15. 6
      libethcore/Ethash.h
  16. 7
      libethcore/Miner.h
  17. 1
      libethereum/CMakeLists.txt
  18. 11
      libethereum/Farm.h
  19. 17
      mix/qml/StateDialog.qml
  20. 4
      mix/qml/StateListModel.qml
  21. 3
      mix/test/qml/TestMain.qml
  22. 20
      mix/test/qml/js/TestMiner.js

19
CMakeLists.txt

@ -63,6 +63,14 @@ function(configureProject)
add_definitions(-DETH_GUI) add_definitions(-DETH_GUI)
endif() endif()
if (CPUID_FOUND)
add_definitions(-DETH_CPUID)
endif()
if (CURL_FOUND)
add_definitions(-DETH_CURL)
endif()
add_definitions(-DETH_TRUE) add_definitions(-DETH_TRUE)
endfunction() endfunction()
@ -149,6 +157,7 @@ else ()
endif () endif ()
# Backwards compatibility # Backwards compatibility
if (HEADLESS) if (HEADLESS)
message("*** WARNING: -DHEADLESS=1 option is DEPRECATED! Use -DBUNDLE=minimal or -DGUI=0")
set(BUNDLE "minimal") set(BUNDLE "minimal")
endif () endif ()
@ -271,8 +280,6 @@ elseif (BUNDLE STREQUAL "user")
set(TESTS OFF) set(TESTS OFF)
endif () endif ()
configureProject()
# Default CMAKE_BUILD_TYPE to "Release". # Default CMAKE_BUILD_TYPE to "Release".
set(CMAKE_BUILD_TYPE CACHE STRING "Release") set(CMAKE_BUILD_TYPE CACHE STRING "Release")
if ("x${CMAKE_BUILD_TYPE}" STREQUAL "x") if ("x${CMAKE_BUILD_TYPE}" STREQUAL "x")
@ -289,6 +296,10 @@ if ("x${TARGET_PLATFORM}" STREQUAL "x")
endif () endif ()
endif () endif ()
include(EthDependencies)
configureProject()
message("------------------------------------------------------------------------") message("------------------------------------------------------------------------")
message("-- CMake Version ${CMAKE_VERSION}") message("-- CMake Version ${CMAKE_VERSION}")
message("-- CMAKE_BUILD_TYPE Build type ${CMAKE_BUILD_TYPE}") message("-- CMAKE_BUILD_TYPE Build type ${CMAKE_BUILD_TYPE}")
@ -296,6 +307,8 @@ message("-- TARGET_PLATFORM Target platform ${TARGET_P
message("-- BUNDLE Build bundle ${BUNDLE}") message("-- BUNDLE Build bundle ${BUNDLE}")
message("--------------------------------------------------------------- features") message("--------------------------------------------------------------- features")
message("-- Chromium support ${ETH_HAVE_WEBENGINE}") message("-- Chromium support ${ETH_HAVE_WEBENGINE}")
message("-- Hardware identification support ${CPUID_FOUND}")
message("-- HTTP Request support ${CURL_FOUND}")
message("-- VMTRACE VM execution tracing ${VMTRACE}") message("-- VMTRACE VM execution tracing ${VMTRACE}")
message("-- PROFILING Profiling support ${PROFILING}") message("-- PROFILING Profiling support ${PROFILING}")
message("-- FATDB Full database exploring ${FATDB}") message("-- FATDB Full database exploring ${FATDB}")
@ -321,9 +334,7 @@ endif ()
include(EthCompilerSettings) include(EthCompilerSettings)
message("-- CXXFLAGS: ${CMAKE_CXX_FLAGS}") message("-- CXXFLAGS: ${CMAKE_CXX_FLAGS}")
# this must be an include, as a function it would mess up with variable scope! # this must be an include, as a function it would mess up with variable scope!
include(EthDependencies)
include(EthExecutableHelper) include(EthExecutableHelper)
createBuildInfo() createBuildInfo()

161
cmake/CMakeParseArguments.cmake

@ -0,0 +1,161 @@
#.rst:
# CMakeParseArguments
# -------------------
#
#
#
# CMAKE_PARSE_ARGUMENTS(<prefix> <options> <one_value_keywords>
# <multi_value_keywords> args...)
#
# CMAKE_PARSE_ARGUMENTS() is intended to be used in macros or functions
# for parsing the arguments given to that macro or function. It
# processes the arguments and defines a set of variables which hold the
# values of the respective options.
#
# The <options> argument contains all options for the respective macro,
# i.e. keywords which can be used when calling the macro without any
# value following, like e.g. the OPTIONAL keyword of the install()
# command.
#
# The <one_value_keywords> argument contains all keywords for this macro
# which are followed by one value, like e.g. DESTINATION keyword of the
# install() command.
#
# The <multi_value_keywords> argument contains all keywords for this
# macro which can be followed by more than one value, like e.g. the
# TARGETS or FILES keywords of the install() command.
#
# When done, CMAKE_PARSE_ARGUMENTS() will have defined for each of the
# keywords listed in <options>, <one_value_keywords> and
# <multi_value_keywords> a variable composed of the given <prefix>
# followed by "_" and the name of the respective keyword. These
# variables will then hold the respective value from the argument list.
# For the <options> keywords this will be TRUE or FALSE.
#
# All remaining arguments are collected in a variable
# <prefix>_UNPARSED_ARGUMENTS, this can be checked afterwards to see
# whether your macro was called with unrecognized parameters.
#
# As an example here a my_install() macro, which takes similar arguments
# as the real install() command:
#
# ::
#
# function(MY_INSTALL)
# set(options OPTIONAL FAST)
# set(oneValueArgs DESTINATION RENAME)
# set(multiValueArgs TARGETS CONFIGURATIONS)
# cmake_parse_arguments(MY_INSTALL "${options}" "${oneValueArgs}"
# "${multiValueArgs}" ${ARGN} )
# ...
#
#
#
# Assume my_install() has been called like this:
#
# ::
#
# my_install(TARGETS foo bar DESTINATION bin OPTIONAL blub)
#
#
#
# After the cmake_parse_arguments() call the macro will have set the
# following variables:
#
# ::
#
# MY_INSTALL_OPTIONAL = TRUE
# MY_INSTALL_FAST = FALSE (this option was not used when calling my_install()
# MY_INSTALL_DESTINATION = "bin"
# MY_INSTALL_RENAME = "" (was not used)
# MY_INSTALL_TARGETS = "foo;bar"
# MY_INSTALL_CONFIGURATIONS = "" (was not used)
# MY_INSTALL_UNPARSED_ARGUMENTS = "blub" (no value expected after "OPTIONAL"
#
#
#
# You can then continue and process these variables.
#
# Keywords terminate lists of values, e.g. if directly after a
# one_value_keyword another recognized keyword follows, this is
# interpreted as the beginning of the new option. E.g.
# my_install(TARGETS foo DESTINATION OPTIONAL) would result in
# MY_INSTALL_DESTINATION set to "OPTIONAL", but MY_INSTALL_DESTINATION
# would be empty and MY_INSTALL_OPTIONAL would be set to TRUE therefor.
#=============================================================================
# Copyright 2010 Alexander Neundorf <neundorf@kde.org>
#
# Distributed under the OSI-approved BSD License (the "License");
# see accompanying file Copyright.txt for details.
#
# This software is distributed WITHOUT ANY WARRANTY; without even the
# implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
# See the License for more information.
#=============================================================================
# (To distribute this file outside of CMake, substitute the full
# License text for the above reference.)
if(__CMAKE_PARSE_ARGUMENTS_INCLUDED)
return()
endif()
set(__CMAKE_PARSE_ARGUMENTS_INCLUDED TRUE)
function(CMAKE_PARSE_ARGUMENTS prefix _optionNames _singleArgNames _multiArgNames)
# first set all result variables to empty/FALSE
foreach(arg_name ${_singleArgNames} ${_multiArgNames})
set(${prefix}_${arg_name})
endforeach()
foreach(option ${_optionNames})
set(${prefix}_${option} FALSE)
endforeach()
set(${prefix}_UNPARSED_ARGUMENTS)
set(insideValues FALSE)
set(currentArgName)
# now iterate over all arguments and fill the result variables
foreach(currentArg ${ARGN})
list(FIND _optionNames "${currentArg}" optionIndex) # ... then this marks the end of the arguments belonging to this keyword
list(FIND _singleArgNames "${currentArg}" singleArgIndex) # ... then this marks the end of the arguments belonging to this keyword
list(FIND _multiArgNames "${currentArg}" multiArgIndex) # ... then this marks the end of the arguments belonging to this keyword
if(${optionIndex} EQUAL -1 AND ${singleArgIndex} EQUAL -1 AND ${multiArgIndex} EQUAL -1)
if(insideValues)
if("${insideValues}" STREQUAL "SINGLE")
set(${prefix}_${currentArgName} ${currentArg})
set(insideValues FALSE)
elseif("${insideValues}" STREQUAL "MULTI")
list(APPEND ${prefix}_${currentArgName} ${currentArg})
endif()
else()
list(APPEND ${prefix}_UNPARSED_ARGUMENTS ${currentArg})
endif()
else()
if(NOT ${optionIndex} EQUAL -1)
set(${prefix}_${currentArg} TRUE)
set(insideValues FALSE)
elseif(NOT ${singleArgIndex} EQUAL -1)
set(currentArgName ${currentArg})
set(${prefix}_${currentArgName})
set(insideValues "SINGLE")
elseif(NOT ${multiArgIndex} EQUAL -1)
set(currentArgName ${currentArg})
set(${prefix}_${currentArgName})
set(insideValues "MULTI")
endif()
endif()
endforeach()
# propagate the result variables to the caller:
foreach(arg_name ${_singleArgNames} ${_multiArgNames} ${_optionNames})
set(${prefix}_${arg_name} ${${prefix}_${arg_name}} PARENT_SCOPE)
endforeach()
set(${prefix}_UNPARSED_ARGUMENTS ${${prefix}_UNPARSED_ARGUMENTS} PARENT_SCOPE)
endfunction()

16
cmake/EthDependencies.cmake

@ -64,7 +64,6 @@ if (JSONRPC)
message(" - microhttpd header: ${MHD_INCLUDE_DIRS}") message(" - microhttpd header: ${MHD_INCLUDE_DIRS}")
message(" - microhttpd lib : ${MHD_LIBRARIES}") message(" - microhttpd lib : ${MHD_LIBRARIES}")
message(" - microhttpd dll : ${MHD_DLLS}") message(" - microhttpd dll : ${MHD_DLLS}")
endif() #JSONRPC endif() #JSONRPC
# TODO readline package does not yet check for correct version number # TODO readline package does not yet check for correct version number
@ -91,7 +90,7 @@ endif()
# TODO it is also not required in msvc build # TODO it is also not required in msvc build
find_package (Gmp 6.0.0) find_package (Gmp 6.0.0)
if (GMP_FOUND) if (GMP_FOUND)
message(" - gmp Header: ${GMP_INCLUDE_DIRS}") message(" - gmp header: ${GMP_INCLUDE_DIRS}")
message(" - gmp lib : ${GMP_LIBRARIES}") message(" - gmp lib : ${GMP_LIBRARIES}")
endif() endif()
@ -101,6 +100,19 @@ find_package (CURL)
message(" - curl header: ${CURL_INCLUDE_DIRS}") message(" - curl header: ${CURL_INCLUDE_DIRS}")
message(" - curl lib : ${CURL_LIBRARIES}") message(" - curl lib : ${CURL_LIBRARIES}")
# cpuid required for eth
find_package (Cpuid)
if (CPUID_FOUND)
message(" - cpuid header: ${CPUID_INCLUDE_DIRS}")
message(" - cpuid lib : ${CPUID_LIBRARIES}")
endif()
find_package (OpenCL)
if (OpenCL_FOUND)
message(" - opencl header: ${OpenCL_INCLUDE_DIRES}")
message(" - opencl lib : ${OpenCL_LIBRARIES}")
endif()
# find location of jsonrpcstub # find location of jsonrpcstub
find_program(ETH_JSON_RPC_STUB jsonrpcstub) find_program(ETH_JSON_RPC_STUB jsonrpcstub)
message(" - jsonrpcstub location : ${ETH_JSON_RPC_STUB}") message(" - jsonrpcstub location : ${ETH_JSON_RPC_STUB}")

33
cmake/FindCpuid.cmake

@ -0,0 +1,33 @@
# Find libcpuid
#
# Find the libcpuid includes and library
#
# if you nee to add a custom library search path, do it via via CMAKE_PREFIX_PATH
#
# This module defines
# CPUID_INCLUDE_DIRS, where to find header, etc.
# CPUID_LIBRARIES, the libraries needed to use cpuid.
# CPUID_FOUND, If false, do not try to use cpuid.
# only look in default directories
find_path(
CPUID_INCLUDE_DIR
NAMES libcpuid/libcpuid.h
DOC "libcpuid include dir"
)
find_library(
CPUID_LIBRARY
NAMES cpuid
DOC "libcpuid library"
)
set(CPUID_INCLUDE_DIRS ${CPUID_INCLUDE_DIR})
set(CPUID_LIBRARIES ${CPUID_LIBRARY})
# handle the QUIETLY and REQUIRED arguments and set CPUID_FOUND to TRUE
# if all listed variables are TRUE, hide their existence from configuration view
include(FindPackageHandleStandardArgs)
find_package_handle_standard_args(cpuid DEFAULT_MSG CPUID_INCLUDE_DIR CPUID_LIBRARY)
mark_as_advanced (CPUID_INCLUDE_DIR CPUID_LIBRARY)

136
cmake/FindOpenCL.cmake

@ -0,0 +1,136 @@
#.rst:
# FindOpenCL
# ----------
#
# Try to find OpenCL
#
# Once done this will define::
#
# OpenCL_FOUND - True if OpenCL was found
# OpenCL_INCLUDE_DIRS - include directories for OpenCL
# OpenCL_LIBRARIES - link against this library to use OpenCL
# OpenCL_VERSION_STRING - Highest supported OpenCL version (eg. 1.2)
# OpenCL_VERSION_MAJOR - The major version of the OpenCL implementation
# OpenCL_VERSION_MINOR - The minor version of the OpenCL implementation
#
# The module will also define two cache variables::
#
# OpenCL_INCLUDE_DIR - the OpenCL include directory
# OpenCL_LIBRARY - the path to the OpenCL library
#
#=============================================================================
# Copyright 2014 Matthaeus G. Chajdas
#
# Distributed under the OSI-approved BSD License (the "License");
# see accompanying file Copyright.txt for details.
#
# This software is distributed WITHOUT ANY WARRANTY; without even the
# implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
# See the License for more information.
#=============================================================================
# (To distribute this file outside of CMake, substitute the full
# License text for the above reference.)
function(_FIND_OPENCL_VERSION)
include(CheckSymbolExists)
include(CMakePushCheckState)
set(CMAKE_REQUIRED_QUIET ${OpenCL_FIND_QUIETLY})
CMAKE_PUSH_CHECK_STATE()
foreach(VERSION "2_0" "1_2" "1_1" "1_0")
set(CMAKE_REQUIRED_INCLUDES "${OpenCL_INCLUDE_DIR}")
if(APPLE)
CHECK_SYMBOL_EXISTS(
CL_VERSION_${VERSION}
"${OpenCL_INCLUDE_DIR}/OpenCL/cl.h"
OPENCL_VERSION_${VERSION})
else()
CHECK_SYMBOL_EXISTS(
CL_VERSION_${VERSION}
"${OpenCL_INCLUDE_DIR}/CL/cl.h"
OPENCL_VERSION_${VERSION})
endif()
if(OPENCL_VERSION_${VERSION})
string(REPLACE "_" "." VERSION "${VERSION}")
set(OpenCL_VERSION_STRING ${VERSION} PARENT_SCOPE)
string(REGEX MATCHALL "[0-9]+" version_components "${VERSION}")
list(GET version_components 0 major_version)
list(GET version_components 1 minor_version)
set(OpenCL_VERSION_MAJOR ${major_version} PARENT_SCOPE)
set(OpenCL_VERSION_MINOR ${minor_version} PARENT_SCOPE)
break()
endif()
endforeach()
CMAKE_POP_CHECK_STATE()
endfunction()
find_path(OpenCL_INCLUDE_DIR
NAMES
CL/cl.h OpenCL/cl.h
PATHS
ENV "PROGRAMFILES(X86)"
ENV AMDAPPSDKROOT
ENV INTELOCLSDKROOT
ENV NVSDKCOMPUTE_ROOT
ENV CUDA_PATH
ENV ATISTREAMSDKROOT
PATH_SUFFIXES
include
OpenCL/common/inc
"AMD APP/include")
_FIND_OPENCL_VERSION()
if(WIN32)
if(CMAKE_SIZEOF_VOID_P EQUAL 4)
find_library(OpenCL_LIBRARY
NAMES OpenCL
PATHS
ENV "PROGRAMFILES(X86)"
ENV AMDAPPSDKROOT
ENV INTELOCLSDKROOT
ENV CUDA_PATH
ENV NVSDKCOMPUTE_ROOT
ENV ATISTREAMSDKROOT
PATH_SUFFIXES
"AMD APP/lib/x86"
lib/x86
lib/Win32
OpenCL/common/lib/Win32)
elseif(CMAKE_SIZEOF_VOID_P EQUAL 8)
find_library(OpenCL_LIBRARY
NAMES OpenCL
PATHS
ENV "PROGRAMFILES(X86)"
ENV AMDAPPSDKROOT
ENV INTELOCLSDKROOT
ENV CUDA_PATH
ENV NVSDKCOMPUTE_ROOT
ENV ATISTREAMSDKROOT
PATH_SUFFIXES
"AMD APP/lib/x86_64"
lib/x86_64
lib/x64
OpenCL/common/lib/x64)
endif()
else()
find_library(OpenCL_LIBRARY
NAMES OpenCL)
endif()
set(OpenCL_LIBRARIES ${OpenCL_LIBRARY})
set(OpenCL_INCLUDE_DIRS ${OpenCL_INCLUDE_DIR})
include(${CMAKE_CURRENT_LIST_DIR}/FindPackageHandleStandardArgs.cmake)
find_package_handle_standard_args(
OpenCL
FOUND_VAR OpenCL_FOUND
REQUIRED_VARS OpenCL_LIBRARY OpenCL_INCLUDE_DIR
VERSION_VAR OpenCL_VERSION_STRING)
mark_as_advanced(
OpenCL_INCLUDE_DIR
OpenCL_LIBRARY)

382
cmake/FindPackageHandleStandardArgs.cmake

@ -0,0 +1,382 @@
#.rst:
# FindPackageHandleStandardArgs
# -----------------------------
#
#
#
# FIND_PACKAGE_HANDLE_STANDARD_ARGS(<name> ... )
#
# This function is intended to be used in FindXXX.cmake modules files.
# It handles the REQUIRED, QUIET and version-related arguments to
# find_package(). It also sets the <packagename>_FOUND variable. The
# package is considered found if all variables <var1>... listed contain
# valid results, e.g. valid filepaths.
#
# There are two modes of this function. The first argument in both
# modes is the name of the Find-module where it is called (in original
# casing).
#
# The first simple mode looks like this:
#
# ::
#
# FIND_PACKAGE_HANDLE_STANDARD_ARGS(<name>
# (DEFAULT_MSG|"Custom failure message") <var1>...<varN> )
#
# If the variables <var1> to <varN> are all valid, then
# <UPPERCASED_NAME>_FOUND will be set to TRUE. If DEFAULT_MSG is given
# as second argument, then the function will generate itself useful
# success and error messages. You can also supply a custom error
# message for the failure case. This is not recommended.
#
# The second mode is more powerful and also supports version checking:
#
# ::
#
# FIND_PACKAGE_HANDLE_STANDARD_ARGS(NAME
# [FOUND_VAR <resultVar>]
# [REQUIRED_VARS <var1>...<varN>]
# [VERSION_VAR <versionvar>]
# [HANDLE_COMPONENTS]
# [CONFIG_MODE]
# [FAIL_MESSAGE "Custom failure message"] )
#
# In this mode, the name of the result-variable can be set either to
# either <UPPERCASED_NAME>_FOUND or <OriginalCase_Name>_FOUND using the
# FOUND_VAR option. Other names for the result-variable are not
# allowed. So for a Find-module named FindFooBar.cmake, the two
# possible names are FooBar_FOUND and FOOBAR_FOUND. It is recommended
# to use the original case version. If the FOUND_VAR option is not
# used, the default is <UPPERCASED_NAME>_FOUND.
#
# As in the simple mode, if <var1> through <varN> are all valid,
# <packagename>_FOUND will be set to TRUE. After REQUIRED_VARS the
# variables which are required for this package are listed. Following
# VERSION_VAR the name of the variable can be specified which holds the
# version of the package which has been found. If this is done, this
# version will be checked against the (potentially) specified required
# version used in the find_package() call. The EXACT keyword is also
# handled. The default messages include information about the required
# version and the version which has been actually found, both if the
# version is ok or not. If the package supports components, use the
# HANDLE_COMPONENTS option to enable handling them. In this case,
# find_package_handle_standard_args() will report which components have
# been found and which are missing, and the <packagename>_FOUND variable
# will be set to FALSE if any of the required components (i.e. not the
# ones listed after OPTIONAL_COMPONENTS) are missing. Use the option
# CONFIG_MODE if your FindXXX.cmake module is a wrapper for a
# find_package(... NO_MODULE) call. In this case VERSION_VAR will be
# set to <NAME>_VERSION and the macro will automatically check whether
# the Config module was found. Via FAIL_MESSAGE a custom failure
# message can be specified, if this is not used, the default message
# will be displayed.
#
# Example for mode 1:
#
# ::
#
# find_package_handle_standard_args(LibXml2 DEFAULT_MSG
# LIBXML2_LIBRARY LIBXML2_INCLUDE_DIR)
#
#
#
# LibXml2 is considered to be found, if both LIBXML2_LIBRARY and
# LIBXML2_INCLUDE_DIR are valid. Then also LIBXML2_FOUND is set to
# TRUE. If it is not found and REQUIRED was used, it fails with
# FATAL_ERROR, independent whether QUIET was used or not. If it is
# found, success will be reported, including the content of <var1>. On
# repeated Cmake runs, the same message won't be printed again.
#
# Example for mode 2:
#
# ::
#
# find_package_handle_standard_args(LibXslt
# FOUND_VAR LibXslt_FOUND
# REQUIRED_VARS LibXslt_LIBRARIES LibXslt_INCLUDE_DIRS
# VERSION_VAR LibXslt_VERSION_STRING)
#
# In this case, LibXslt is considered to be found if the variable(s)
# listed after REQUIRED_VAR are all valid, i.e. LibXslt_LIBRARIES and
# LibXslt_INCLUDE_DIRS in this case. The result will then be stored in
# LibXslt_FOUND . Also the version of LibXslt will be checked by using
# the version contained in LibXslt_VERSION_STRING. Since no
# FAIL_MESSAGE is given, the default messages will be printed.
#
# Another example for mode 2:
#
# ::
#
# find_package(Automoc4 QUIET NO_MODULE HINTS /opt/automoc4)
# find_package_handle_standard_args(Automoc4 CONFIG_MODE)
#
# In this case, FindAutmoc4.cmake wraps a call to find_package(Automoc4
# NO_MODULE) and adds an additional search directory for automoc4. Here
# the result will be stored in AUTOMOC4_FOUND. The following
# FIND_PACKAGE_HANDLE_STANDARD_ARGS() call produces a proper
# success/error message.
#=============================================================================
# Copyright 2007-2009 Kitware, Inc.
#
# Distributed under the OSI-approved BSD License (the "License");
# see accompanying file Copyright.txt for details.
#
# This software is distributed WITHOUT ANY WARRANTY; without even the
# implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
# See the License for more information.
#=============================================================================
# (To distribute this file outside of CMake, substitute the full
# License text for the above reference.)
include(${CMAKE_CURRENT_LIST_DIR}/FindPackageMessage.cmake)
include(${CMAKE_CURRENT_LIST_DIR}/CMakeParseArguments.cmake)
# internal helper macro
macro(_FPHSA_FAILURE_MESSAGE _msg)
if (${_NAME}_FIND_REQUIRED)
message(FATAL_ERROR "${_msg}")
else ()
if (NOT ${_NAME}_FIND_QUIETLY)
message(STATUS "${_msg}")
endif ()
endif ()
endmacro()
# internal helper macro to generate the failure message when used in CONFIG_MODE:
macro(_FPHSA_HANDLE_FAILURE_CONFIG_MODE)
# <name>_CONFIG is set, but FOUND is false, this means that some other of the REQUIRED_VARS was not found:
if(${_NAME}_CONFIG)
_FPHSA_FAILURE_MESSAGE("${FPHSA_FAIL_MESSAGE}: missing: ${MISSING_VARS} (found ${${_NAME}_CONFIG} ${VERSION_MSG})")
else()
# If _CONSIDERED_CONFIGS is set, the config-file has been found, but no suitable version.
# List them all in the error message:
if(${_NAME}_CONSIDERED_CONFIGS)
set(configsText "")
list(LENGTH ${_NAME}_CONSIDERED_CONFIGS configsCount)
math(EXPR configsCount "${configsCount} - 1")
foreach(currentConfigIndex RANGE ${configsCount})
list(GET ${_NAME}_CONSIDERED_CONFIGS ${currentConfigIndex} filename)
list(GET ${_NAME}_CONSIDERED_VERSIONS ${currentConfigIndex} version)
set(configsText "${configsText} ${filename} (version ${version})\n")
endforeach()
if (${_NAME}_NOT_FOUND_MESSAGE)
set(configsText "${configsText} Reason given by package: ${${_NAME}_NOT_FOUND_MESSAGE}\n")
endif()
_FPHSA_FAILURE_MESSAGE("${FPHSA_FAIL_MESSAGE} ${VERSION_MSG}, checked the following files:\n${configsText}")
else()
# Simple case: No Config-file was found at all:
_FPHSA_FAILURE_MESSAGE("${FPHSA_FAIL_MESSAGE}: found neither ${_NAME}Config.cmake nor ${_NAME_LOWER}-config.cmake ${VERSION_MSG}")
endif()
endif()
endmacro()
function(FIND_PACKAGE_HANDLE_STANDARD_ARGS _NAME _FIRST_ARG)
# set up the arguments for CMAKE_PARSE_ARGUMENTS and check whether we are in
# new extended or in the "old" mode:
set(options CONFIG_MODE HANDLE_COMPONENTS)
set(oneValueArgs FAIL_MESSAGE VERSION_VAR FOUND_VAR)
set(multiValueArgs REQUIRED_VARS)
set(_KEYWORDS_FOR_EXTENDED_MODE ${options} ${oneValueArgs} ${multiValueArgs} )
list(FIND _KEYWORDS_FOR_EXTENDED_MODE "${_FIRST_ARG}" INDEX)
if(${INDEX} EQUAL -1)
set(FPHSA_FAIL_MESSAGE ${_FIRST_ARG})
set(FPHSA_REQUIRED_VARS ${ARGN})
set(FPHSA_VERSION_VAR)
else()
CMAKE_PARSE_ARGUMENTS(FPHSA "${options}" "${oneValueArgs}" "${multiValueArgs}" ${_FIRST_ARG} ${ARGN})
if(FPHSA_UNPARSED_ARGUMENTS)
message(FATAL_ERROR "Unknown keywords given to FIND_PACKAGE_HANDLE_STANDARD_ARGS(): \"${FPHSA_UNPARSED_ARGUMENTS}\"")
endif()
if(NOT FPHSA_FAIL_MESSAGE)
set(FPHSA_FAIL_MESSAGE "DEFAULT_MSG")
endif()
endif()
# now that we collected all arguments, process them
if("x${FPHSA_FAIL_MESSAGE}" STREQUAL "xDEFAULT_MSG")
set(FPHSA_FAIL_MESSAGE "Could NOT find ${_NAME}")
endif()
# In config-mode, we rely on the variable <package>_CONFIG, which is set by find_package()
# when it successfully found the config-file, including version checking:
if(FPHSA_CONFIG_MODE)
list(INSERT FPHSA_REQUIRED_VARS 0 ${_NAME}_CONFIG)
list(REMOVE_DUPLICATES FPHSA_REQUIRED_VARS)
set(FPHSA_VERSION_VAR ${_NAME}_VERSION)
endif()
if(NOT FPHSA_REQUIRED_VARS)
message(FATAL_ERROR "No REQUIRED_VARS specified for FIND_PACKAGE_HANDLE_STANDARD_ARGS()")
endif()
list(GET FPHSA_REQUIRED_VARS 0 _FIRST_REQUIRED_VAR)
string(TOUPPER ${_NAME} _NAME_UPPER)
string(TOLOWER ${_NAME} _NAME_LOWER)
if(FPHSA_FOUND_VAR)
if(FPHSA_FOUND_VAR MATCHES "^${_NAME}_FOUND$" OR FPHSA_FOUND_VAR MATCHES "^${_NAME_UPPER}_FOUND$")
set(_FOUND_VAR ${FPHSA_FOUND_VAR})
else()
message(FATAL_ERROR "The argument for FOUND_VAR is \"${FPHSA_FOUND_VAR}\", but only \"${_NAME}_FOUND\" and \"${_NAME_UPPER}_FOUND\" are valid names.")
endif()
else()
set(_FOUND_VAR ${_NAME_UPPER}_FOUND)
endif()
# collect all variables which were not found, so they can be printed, so the
# user knows better what went wrong (#6375)
set(MISSING_VARS "")
set(DETAILS "")
# check if all passed variables are valid
unset(${_FOUND_VAR})
foreach(_CURRENT_VAR ${FPHSA_REQUIRED_VARS})
if(NOT ${_CURRENT_VAR})
set(${_FOUND_VAR} FALSE)
set(MISSING_VARS "${MISSING_VARS} ${_CURRENT_VAR}")
else()
set(DETAILS "${DETAILS}[${${_CURRENT_VAR}}]")
endif()
endforeach()
if(NOT "${${_FOUND_VAR}}" STREQUAL "FALSE")
set(${_FOUND_VAR} TRUE)
endif()
# component handling
unset(FOUND_COMPONENTS_MSG)
unset(MISSING_COMPONENTS_MSG)
if(FPHSA_HANDLE_COMPONENTS)
foreach(comp ${${_NAME}_FIND_COMPONENTS})
if(${_NAME}_${comp}_FOUND)
if(NOT DEFINED FOUND_COMPONENTS_MSG)
set(FOUND_COMPONENTS_MSG "found components: ")
endif()
set(FOUND_COMPONENTS_MSG "${FOUND_COMPONENTS_MSG} ${comp}")
else()
if(NOT DEFINED MISSING_COMPONENTS_MSG)
set(MISSING_COMPONENTS_MSG "missing components: ")
endif()
set(MISSING_COMPONENTS_MSG "${MISSING_COMPONENTS_MSG} ${comp}")
if(${_NAME}_FIND_REQUIRED_${comp})
set(${_FOUND_VAR} FALSE)
set(MISSING_VARS "${MISSING_VARS} ${comp}")
endif()
endif()
endforeach()
set(COMPONENT_MSG "${FOUND_COMPONENTS_MSG} ${MISSING_COMPONENTS_MSG}")
set(DETAILS "${DETAILS}[c${COMPONENT_MSG}]")
endif()
# version handling:
set(VERSION_MSG "")
set(VERSION_OK TRUE)
set(VERSION ${${FPHSA_VERSION_VAR}})
# check with DEFINED here as the requested or found version may be "0"
if (DEFINED ${_NAME}_FIND_VERSION)
if(DEFINED ${FPHSA_VERSION_VAR})
if(${_NAME}_FIND_VERSION_EXACT) # exact version required
# count the dots in the version string
string(REGEX REPLACE "[^.]" "" _VERSION_DOTS "${VERSION}")
# add one dot because there is one dot more than there are components
string(LENGTH "${_VERSION_DOTS}." _VERSION_DOTS)
if (_VERSION_DOTS GREATER ${_NAME}_FIND_VERSION_COUNT)
# Because of the C++ implementation of find_package() ${_NAME}_FIND_VERSION_COUNT
# is at most 4 here. Therefore a simple lookup table is used.
if (${_NAME}_FIND_VERSION_COUNT EQUAL 1)
set(_VERSION_REGEX "[^.]*")
elseif (${_NAME}_FIND_VERSION_COUNT EQUAL 2)
set(_VERSION_REGEX "[^.]*\\.[^.]*")
elseif (${_NAME}_FIND_VERSION_COUNT EQUAL 3)
set(_VERSION_REGEX "[^.]*\\.[^.]*\\.[^.]*")
else ()
set(_VERSION_REGEX "[^.]*\\.[^.]*\\.[^.]*\\.[^.]*")
endif ()
string(REGEX REPLACE "^(${_VERSION_REGEX})\\..*" "\\1" _VERSION_HEAD "${VERSION}")
unset(_VERSION_REGEX)
if (NOT ${_NAME}_FIND_VERSION VERSION_EQUAL _VERSION_HEAD)
set(VERSION_MSG "Found unsuitable version \"${VERSION}\", but required is exact version \"${${_NAME}_FIND_VERSION}\"")
set(VERSION_OK FALSE)
else ()
set(VERSION_MSG "(found suitable exact version \"${VERSION}\")")
endif ()
unset(_VERSION_HEAD)
else ()
if (NOT "${${_NAME}_FIND_VERSION}" VERSION_EQUAL "${VERSION}")
set(VERSION_MSG "Found unsuitable version \"${VERSION}\", but required is exact version \"${${_NAME}_FIND_VERSION}\"")
set(VERSION_OK FALSE)
else ()
set(VERSION_MSG "(found suitable exact version \"${VERSION}\")")
endif ()
endif ()
unset(_VERSION_DOTS)
else() # minimum version specified:
if ("${${_NAME}_FIND_VERSION}" VERSION_GREATER "${VERSION}")
set(VERSION_MSG "Found unsuitable version \"${VERSION}\", but required is at least \"${${_NAME}_FIND_VERSION}\"")
set(VERSION_OK FALSE)
else ()
set(VERSION_MSG "(found suitable version \"${VERSION}\", minimum required is \"${${_NAME}_FIND_VERSION}\")")
endif ()
endif()
else()
# if the package was not found, but a version was given, add that to the output:
if(${_NAME}_FIND_VERSION_EXACT)
set(VERSION_MSG "(Required is exact version \"${${_NAME}_FIND_VERSION}\")")
else()
set(VERSION_MSG "(Required is at least version \"${${_NAME}_FIND_VERSION}\")")
endif()
endif()
else ()
if(VERSION)
set(VERSION_MSG "(found version \"${VERSION}\")")
endif()
endif ()
if(VERSION_OK)
set(DETAILS "${DETAILS}[v${VERSION}(${${_NAME}_FIND_VERSION})]")
else()
set(${_FOUND_VAR} FALSE)
endif()
# print the result:
if (${_FOUND_VAR})
FIND_PACKAGE_MESSAGE(${_NAME} "Found ${_NAME}: ${${_FIRST_REQUIRED_VAR}} ${VERSION_MSG} ${COMPONENT_MSG}" "${DETAILS}")
else ()
if(FPHSA_CONFIG_MODE)
_FPHSA_HANDLE_FAILURE_CONFIG_MODE()
else()
if(NOT VERSION_OK)
_FPHSA_FAILURE_MESSAGE("${FPHSA_FAIL_MESSAGE}: ${VERSION_MSG} (found ${${_FIRST_REQUIRED_VAR}})")
else()
_FPHSA_FAILURE_MESSAGE("${FPHSA_FAIL_MESSAGE} (missing: ${MISSING_VARS}) ${VERSION_MSG}")
endif()
endif()
endif ()
set(${_FOUND_VAR} ${${_FOUND_VAR}} PARENT_SCOPE)
endfunction()

57
cmake/FindPackageMessage.cmake

@ -0,0 +1,57 @@
#.rst:
# FindPackageMessage
# ------------------
#
#
#
# FIND_PACKAGE_MESSAGE(<name> "message for user" "find result details")
#
# This macro is intended to be used in FindXXX.cmake modules files. It
# will print a message once for each unique find result. This is useful
# for telling the user where a package was found. The first argument
# specifies the name (XXX) of the package. The second argument
# specifies the message to display. The third argument lists details
# about the find result so that if they change the message will be
# displayed again. The macro also obeys the QUIET argument to the
# find_package command.
#
# Example:
#
# ::
#
# if(X11_FOUND)
# FIND_PACKAGE_MESSAGE(X11 "Found X11: ${X11_X11_LIB}"
# "[${X11_X11_LIB}][${X11_INCLUDE_DIR}]")
# else()
# ...
# endif()
#=============================================================================
# Copyright 2008-2009 Kitware, Inc.
#
# Distributed under the OSI-approved BSD License (the "License");
# see accompanying file Copyright.txt for details.
#
# This software is distributed WITHOUT ANY WARRANTY; without even the
# implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
# See the License for more information.
#=============================================================================
# (To distribute this file outside of CMake, substitute the full
# License text for the above reference.)
function(FIND_PACKAGE_MESSAGE pkg msg details)
# Avoid printing a message repeatedly for the same find result.
if(NOT ${pkg}_FIND_QUIETLY)
string(REPLACE "\n" "" details "${details}")
set(DETAILS_VAR FIND_PACKAGE_MESSAGE_DETAILS_${pkg})
if(NOT "${details}" STREQUAL "${${DETAILS_VAR}}")
# The message has not yet been printed.
message(STATUS "${msg}")
# Save the find details in the cache to avoid printing the same
# message again.
set("${DETAILS_VAR}" "${details}"
CACHE INTERNAL "Details about finding ${pkg}")
endif()
endif()
endfunction()

1
eth/CMakeLists.txt

@ -27,6 +27,7 @@ endif()
target_link_libraries(${EXECUTABLE} webthree) target_link_libraries(${EXECUTABLE} webthree)
target_link_libraries(${EXECUTABLE} ethash) target_link_libraries(${EXECUTABLE} ethash)
target_link_libraries(${EXECUTABLE} ethash-cl)
if (DEFINED WIN32 AND NOT DEFINED CMAKE_COMPILER_IS_MINGW) if (DEFINED WIN32 AND NOT DEFINED CMAKE_COMPILER_IS_MINGW)
eth_copy_dlls("${EXECUTABLE}" MHD_DLLS) eth_copy_dlls("${EXECUTABLE}" MHD_DLLS)

192
eth/main.cpp

@ -38,14 +38,17 @@
#include <libevm/VMFactory.h> #include <libevm/VMFactory.h>
#include <libethereum/All.h> #include <libethereum/All.h>
#include <libwebthree/WebThree.h> #include <libwebthree/WebThree.h>
#if ETH_READLINE #if ETH_READLINE || !ETH_TRUE
#include <readline/readline.h> #include <readline/readline.h>
#include <readline/history.h> #include <readline/history.h>
#endif #endif
#if ETH_JSONRPC #if ETH_JSONRPC || !ETH_TRUE
#include <libweb3jsonrpc/WebThreeStubServer.h> #include <libweb3jsonrpc/WebThreeStubServer.h>
#include <jsonrpccpp/server/connectors/httpserver.h> #include <jsonrpccpp/server/connectors/httpserver.h>
#endif #endif
#if ETH_CURL || !ETH_TRUE
#include <curl/curl.h>
#endif
#include "BuildInfo.h" #include "BuildInfo.h"
using namespace std; using namespace std;
using namespace dev; using namespace dev;
@ -89,7 +92,7 @@ void interactiveHelp()
<< " send Execute a given transaction with current secret." << endl << " send Execute a given transaction with current secret." << endl
<< " contract Create a new contract with current secret." << endl << " contract Create a new contract with current secret." << endl
<< " peers List the peers that are connected" << endl << " peers List the peers that are connected" << endl
#if ETH_FATDB #if ETH_FATDB || !ETH_TRUE
<< " listaccounts List the accounts on the network." << endl << " listaccounts List the accounts on the network." << endl
<< " listcontracts List the contracts on the network." << endl << " listcontracts List the contracts on the network." << endl
#endif #endif
@ -112,24 +115,31 @@ void help()
<< " -b,--bootstrap Connect to the default Ethereum peerserver." << endl << " -b,--bootstrap Connect to the default Ethereum peerserver." << endl
<< " -B,--block-fees <n> Set the block fee profit in the reference unit e.g. ¢ (Default: 15)." << endl << " -B,--block-fees <n> Set the block fee profit in the reference unit e.g. ¢ (Default: 15)." << endl
<< " -c,--client-name <name> Add a name to your client's version string (default: blank)." << endl << " -c,--client-name <name> Add a name to your client's version string (default: blank)." << endl
<< " -C,--check-pow <headerHash> <seedHash> <difficulty> <nonce> Check PoW credentials for validity." << endl << " -C,--cpu When mining, use the CPU." << endl
<< " -d,--db-path <path> Load database from path (default: ~/.ethereum " << endl << " -d,--db-path <path> Load database from path (default: ~/.ethereum " << endl
<< " <APPDATA>/Etherum or Library/Application Support/Ethereum)." << endl << " <APPDATA>/Etherum or Library/Application Support/Ethereum)." << endl
<< " --benchmark-warmup <seconds> Set the duration of warmup for the benchmark tests (default: 15)." << endl
<< " --benchmark-trial <seconds> Set the duration for each trial for the benchmark tests (default: 3)." << endl
<< " --benchmark-trials <n> Set the duration of warmup for the benchmark tests (default: 5)." << endl
<< " -D,--create-dag <this/next/number> Create the DAG in preparation for mining on given block and exit." << endl << " -D,--create-dag <this/next/number> Create the DAG in preparation for mining on given block and exit." << endl
<< " -e,--ether-price <n> Set the ether price in the reference unit e.g. ¢ (Default: 30.679)." << endl << " -e,--ether-price <n> Set the ether price in the reference unit e.g. ¢ (Default: 30.679)." << endl
<< " -E,--export <file> Export file as a concatenated series of blocks and exit." << endl << " -E,--export <file> Export file as a concatenated series of blocks and exit." << endl
<< " --from <n> Export only from block n; n may be a decimal, a '0x' prefixed hash, or 'latest'." << endl << " --from <n> Export only from block n; n may be a decimal, a '0x' prefixed hash, or 'latest'." << endl
<< " --to <n> Export only to block n (inclusive); n may be a decimal, a '0x' prefixed hash, or 'latest'." << endl << " --to <n> Export only to block n (inclusive); n may be a decimal, a '0x' prefixed hash, or 'latest'." << endl
<< " --only <n> Equivalent to --export-from n --export-to n." << endl << " --only <n> Equivalent to --export-from n --export-to n." << endl
<< " -f,--force-mining Mine even when there are no transaction to mine (Default: off)" << endl << " -f,--force-mining Mine even when there are no transactions to mine (Default: off)" << endl
#if ETH_JSONRPC || !ETH_TRUE
<< " -F,--farm Put into mining farm mode (default GPU with CPU as fallback)." << endl
#endif
<< " -G,--gpu When mining use the GPU." << endl
<< " -h,--help Show this help message and exit." << endl << " -h,--help Show this help message and exit." << endl
<< " -i,--interactive Enter interactive mode (default: non-interactive)." << endl << " -i,--interactive Enter interactive mode (default: non-interactive)." << endl
<< " -I,--import <file> Import file as a concatenated series of blocks and exit." << endl << " -I,--import <file> Import file as a concatenated series of blocks and exit." << endl
#if ETH_JSONRPC #if ETH_JSONRPC || !ETH_TRUE
<< " -j,--json-rpc Enable JSON-RPC server (default: off)." << endl << " -j,--json-rpc Enable JSON-RPC server (default: off)." << endl
<< " --json-rpc-port Specify JSON-RPC server port (implies '-j', default: " << SensibleHttpPort << ")." << endl << " --json-rpc-port Specify JSON-RPC server port (implies '-j', default: " << SensibleHttpPort << ")." << endl
#endif #endif
#if ETH_EVMJIT #if ETH_EVMJIT || !ETH_TRUE
<< " -J,--jit Enable EVM JIT (default: off)." << endl << " -J,--jit Enable EVM JIT (default: off)." << endl
#endif #endif
<< " -K,--kill First kill the blockchain." << endl << " -K,--kill First kill the blockchain." << endl
@ -137,17 +147,21 @@ void help()
<< " -l,--listen <ip> Listen on the given IP for incoming connections (default: 0.0.0.0)." << endl << " -l,--listen <ip> Listen on the given IP for incoming connections (default: 0.0.0.0)." << endl
<< " -u,--public-ip <ip> Force public ip to given (default: auto)." << endl << " -u,--public-ip <ip> Force public ip to given (default: auto)." << endl
<< " -m,--mining <on/off/number> Enable mining, optionally for a specified number of blocks (Default: off)" << endl << " -m,--mining <on/off/number> Enable mining, optionally for a specified number of blocks (Default: off)" << endl
<< " -n,-u,--upnp <on/off> Use upnp for NAT (default: on)." << endl << " -M,--benchmark Benchmark for mining and exit; use with --cpu and --gpu." << endl
<< " -o,--mode <full/peer> Start a full node or a peer node (Default: full)." << endl << " -o,--mode <full/peer> Start a full node or a peer node (Default: full)." << endl
<< " --opencl-device <n> When mining use OpenCL device n (default: 0)." << endl
<< " -p,--port <port> Connect to remote port (default: 30303)." << endl << " -p,--port <port> Connect to remote port (default: 30303)." << endl
<< " -P,--priority <0 - 100> Default % priority of a transaction (default: 50)." << endl << " -P,--priority <0 - 100> Default % priority of a transaction (default: 50)." << endl
<< " --phone-home <on/off> When benchmarking, publish results (Default: on)" << endl
<< " -R,--rebuild First rebuild the blockchain from the existing database." << endl << " -R,--rebuild First rebuild the blockchain from the existing database." << endl
<< " -r,--remote <host> Connect to remote host (default: none)." << endl << " -r,--remote <host> Connect to remote host (default: none)." << endl
<< " -s,--secret <secretkeyhex> Set the secret key for use with send command (default: auto)." << endl << " -s,--secret <secretkeyhex> Set the secret key for use with send command (default: auto)." << endl
<< " -S,--temporary-secret <secretkeyhex> Set the secret key for use with send command, for this session only." << endl << " -S,--temporary-secret <secretkeyhex> Set the secret key for use with send command, for this session only." << endl
<< " -u,--upnp <on/off> Use upnp for NAT (default: on)." << endl
<< " -v,--verbosity <0 - 9> Set the log verbosity from 0 to 9 (Default: 8)." << endl << " -v,--verbosity <0 - 9> Set the log verbosity from 0 to 9 (Default: 8)." << endl
<< " -x,--peers <number> Attempt to connect to given number of peers (Default: 5)." << endl
<< " -V,--version Show the version and exit." << endl << " -V,--version Show the version and exit." << endl
<< " -w,--check-pow <headerHash> <seedHash> <difficulty> <nonce> Check PoW credentials for validity." << endl
<< " -x,--peers <number> Attempt to connect to given number of peers (Default: 5)." << endl
; ;
exit(0); exit(0);
} }
@ -221,7 +235,9 @@ enum class OperationMode
Node, Node,
Import, Import,
Export, Export,
DAGInit DAGInit,
Benchmark,
Farm
}; };
enum class Format enum class Format
@ -231,6 +247,80 @@ enum class Format
Human Human
}; };
enum class MinerType
{
CPU,
GPU
};
void doBenchmark(MinerType _m, bool _phoneHome, unsigned _warmupDuration = 15, unsigned _trialDuration = 3, unsigned _trials = 5)
{
BlockInfo genesis = CanonBlockChain::genesis();
genesis.difficulty = 1 << 18;
cdebug << genesis.boundary();
GenericFarm<Ethash> f;
f.onSolutionFound([&](ProofOfWork::Solution) { return false; });
string platformInfo = _m == MinerType::CPU ? ProofOfWork::CPUMiner::platformInfo() : _m == MinerType::GPU ? ProofOfWork::GPUMiner::platformInfo() : "";
cout << "Benchmarking on platform: " << platformInfo << endl;
cout << "Preparing DAG..." << endl;
Ethash::prep(genesis);
genesis.difficulty = u256(1) << 63;
genesis.noteDirty();
f.setWork(genesis);
if (_m == MinerType::CPU)
f.startCPU();
else if (_m == MinerType::GPU)
f.startGPU();
map<uint64_t, MiningProgress> results;
uint64_t mean = 0;
uint64_t innerMean = 0;
for (unsigned i = 0; i <= _trials; ++i)
{
if (!i)
cout << "Warming up..." << endl;
else
cout << "Trial " << i << "... " << flush;
this_thread::sleep_for(chrono::seconds(i ? _trialDuration : _warmupDuration));
auto mp = f.miningProgress();
f.resetMiningProgress();
if (!i)
continue;
auto rate = mp.rate();
cout << rate << endl;
results[rate] = mp;
mean += rate;
if (i > 1 && i < 5)
innerMean += rate;
}
f.stop();
cout << "min/mean/max: " << results.begin()->second.rate() << "/" << (mean / _trials) << "/" << results.rbegin()->second.rate() << " H/s" << endl;
cout << "inner mean: " << (innerMean / (_trials - 2)) << " H/s" << endl;
(void)_phoneHome;
if (_phoneHome)
{
cout << "Phoning home to find world ranking..." << endl;
// TODO: send f.miningInfo() along with f.platformInfo() to Marian.
}
exit(0);
}
void doFarm(MinerType _m)
{
(void)_m;
// TODO: Set up JSONRPC client: to implement:
// { "name": "eth_getWork", "params": [], "order": [], "returns": [<powHash>, <seedHash>, <boundary>]},
// { "name": "eth_submitWork", "params": [<nonce>, <mixHash>], "order": [], "returns": true},
}
int main(int argc, char** argv) int main(int argc, char** argv)
{ {
// Init defaults // Init defaults
@ -240,6 +330,10 @@ int main(int argc, char** argv)
OperationMode mode = OperationMode::Node; OperationMode mode = OperationMode::Node;
string dbPath; string dbPath;
/// Mining options
MinerType minerType = MinerType::CPU;
unsigned openclDevice = 0;
/// File name for import/export. /// File name for import/export.
string filename; string filename;
@ -287,6 +381,12 @@ int main(int argc, char** argv)
double etherPrice = 30.679; double etherPrice = 30.679;
double blockFees = 15.0; double blockFees = 15.0;
/// Benchmarking params
bool phoneHome = true;
unsigned benchmarkWarmup = 15;
unsigned benchmarkTrial = 3;
unsigned benchmarkTrials = 5;
string configFile = getDataDir() + "/config.rlp"; string configFile = getDataDir() + "/config.rlp";
bytes b = contents(configFile); bytes b = contents(configFile);
if (b.size()) if (b.size())
@ -319,6 +419,30 @@ int main(int argc, char** argv)
mode = OperationMode::Export; mode = OperationMode::Export;
filename = argv[++i]; filename = argv[++i];
} }
else if (arg == "-F" || arg == "--farm")
mode = OperationMode::Farm;
else if (arg == "--opencl-device" && i + 1 < argc)
try {
openclDevice = stol(argv[++i]);
}
catch (...)
{
cerr << "Bad " << arg << " option: " << argv[i] << endl;
return -1;
}
else if (arg == "--phone-home" && i + 1 < argc)
{
string m = argv[++i];
if (isTrue(m))
phoneHome = true;
else if (isFalse(m))
phoneHome = false;
else
{
cerr << "Bad " << arg << " option: " << m << endl;
return -1;
}
}
else if (arg == "--format" && i + 1 < argc) else if (arg == "--format" && i + 1 < argc)
{ {
string m = argv[++i]; string m = argv[++i];
@ -342,6 +466,8 @@ int main(int argc, char** argv)
exportTo = exportFrom = argv[++i]; exportTo = exportFrom = argv[++i];
else if ((arg == "-n" || arg == "-u" || arg == "--upnp") && i + 1 < argc) else if ((arg == "-n" || arg == "-u" || arg == "--upnp") && i + 1 < argc)
{ {
if (arg == "-n")
cerr << "-n is DEPRECATED. It will be removed for the Frontier. Use -u instead." << endl;
string m = argv[++i]; string m = argv[++i];
if (isTrue(m)) if (isTrue(m))
upnp = true; upnp = true;
@ -353,6 +479,33 @@ int main(int argc, char** argv)
return -1; return -1;
} }
} }
else if (arg == "--benchmark-warmup" && i + 1 < argc)
try {
benchmarkWarmup = stol(argv[++i]);
}
catch (...)
{
cerr << "Bad " << arg << " option: " << argv[i] << endl;
return -1;
}
else if (arg == "--benchmark-trial" && i + 1 < argc)
try {
benchmarkTrial = stol(argv[++i]);
}
catch (...)
{
cerr << "Bad " << arg << " option: " << argv[i] << endl;
return -1;
}
else if (arg == "--benchmark-trials" && i + 1 < argc)
try {
benchmarkTrials = stol(argv[++i]);
}
catch (...)
{
cerr << "Bad " << arg << " option: " << argv[i] << endl;
return -1;
}
else if (arg == "-K" || arg == "--kill-blockchain" || arg == "--kill") else if (arg == "-K" || arg == "--kill-blockchain" || arg == "--kill")
killChain = WithExisting::Kill; killChain = WithExisting::Kill;
else if (arg == "-B" || arg == "--rebuild") else if (arg == "-B" || arg == "--rebuild")
@ -360,8 +513,7 @@ int main(int argc, char** argv)
else if ((arg == "-c" || arg == "--client-name") && i + 1 < argc) else if ((arg == "-c" || arg == "--client-name") && i + 1 < argc)
clientName = argv[++i]; clientName = argv[++i];
else if ((arg == "-a" || arg == "--address" || arg == "--coinbase-address") && i + 1 < argc) else if ((arg == "-a" || arg == "--address" || arg == "--coinbase-address") && i + 1 < argc)
try try {
{
coinbase = h160(fromHex(argv[++i], WhenError::Throw)); coinbase = h160(fromHex(argv[++i], WhenError::Throw));
} }
catch (BadHexCharacter&) catch (BadHexCharacter&)
@ -374,6 +526,10 @@ int main(int argc, char** argv)
cerr << "Bad " << arg << " option: " << argv[i] << endl; cerr << "Bad " << arg << " option: " << argv[i] << endl;
return -1; return -1;
} }
else if (arg == "-C" || arg == "--cpu")
minerType = MinerType::CPU;
else if (arg == "-G" || arg == "--gpu")
minerType = MinerType::GPU;
else if ((arg == "-s" || arg == "--secret") && i + 1 < argc) else if ((arg == "-s" || arg == "--secret") && i + 1 < argc)
sigKey = KeyPair(h256(fromHex(argv[++i]))); sigKey = KeyPair(h256(fromHex(argv[++i])));
else if ((arg == "-S" || arg == "--session-secret") && i + 1 < argc) else if ((arg == "-S" || arg == "--session-secret") && i + 1 < argc)
@ -403,7 +559,7 @@ int main(int argc, char** argv)
return -1; return -1;
} }
} }
else if ((arg == "-C" || arg == "--check-pow") && i + 4 < argc) else if ((arg == "-w" || arg == "--check-pow") && i + 4 < argc)
{ {
string m; string m;
try try
@ -440,6 +596,8 @@ int main(int argc, char** argv)
return -1; return -1;
} }
} }
else if (arg == "-M" || arg == "--benchmark")
mode = OperationMode::Benchmark;
else if ((arg == "-B" || arg == "--block-fees") && i + 1 < argc) else if ((arg == "-B" || arg == "--block-fees") && i + 1 < argc)
{ {
try try
@ -557,11 +715,19 @@ int main(int argc, char** argv)
if (sessionSecret) if (sessionSecret)
sigKey = KeyPair(sessionSecret); sigKey = KeyPair(sessionSecret);
ProofOfWork::GPUMiner::setDefaultDevice(openclDevice);
// Two codepaths is necessary since named block require database, but numbered // Two codepaths is necessary since named block require database, but numbered
// blocks are superuseful to have when database is already open in another process. // blocks are superuseful to have when database is already open in another process.
if (mode == OperationMode::DAGInit && !(initDAG == LatestBlock || initDAG == PendingBlock)) if (mode == OperationMode::DAGInit && !(initDAG == LatestBlock || initDAG == PendingBlock))
doInitDAG(initDAG); doInitDAG(initDAG);
if (mode == OperationMode::Benchmark)
doBenchmark(minerType, phoneHome, benchmarkWarmup, benchmarkTrial, benchmarkTrials);
if (mode == OperationMode::Farm)
doFarm(minerType);
if (!clientName.empty()) if (!clientName.empty())
clientName += "/"; clientName += "/";

48
libethash-cl/CMakeLists.txt

@ -1,47 +1,19 @@
cmake_minimum_required(VERSION 2.8) set(EXECUTABLE ethash-cl)
set(LIBRARY ethash-cl)
#set(CMAKE_BUILD_TYPE Release)
include(bin2h.cmake) include(bin2h.cmake)
bin2h(SOURCE_FILE ethash_cl_miner_kernel.cl bin2h(SOURCE_FILE ethash_cl_miner_kernel.cl
VARIABLE_NAME ethash_cl_miner_kernel VARIABLE_NAME ethash_cl_miner_kernel
HEADER_FILE ${CMAKE_CURRENT_BINARY_DIR}/ethash_cl_miner_kernel.h) HEADER_FILE ${CMAKE_CURRENT_BINARY_DIR}/ethash_cl_miner_kernel.h)
if (NOT MSVC) aux_source_directory(. SRC_LIST)
# Initialize CXXFLAGS for c++11 file(GLOB HEADERS "*.h")
set(CMAKE_CXX_FLAGS "-Wall -std=c++11")
set(CMAKE_CXX_FLAGS_DEBUG "-O0 -g")
set(CMAKE_CXX_FLAGS_MINSIZEREL "-Os -DNDEBUG")
set(CMAKE_CXX_FLAGS_RELEASE "-O4 -DNDEBUG")
set(CMAKE_CXX_FLAGS_RELWITHDEBINFO "-O2 -g")
# Compiler-specific C++11 activation.
if ("${CMAKE_CXX_COMPILER_ID}" MATCHES "GNU")
execute_process(
COMMAND ${CMAKE_CXX_COMPILER} -dumpversion OUTPUT_VARIABLE GCC_VERSION)
if (NOT (GCC_VERSION VERSION_GREATER 4.7 OR GCC_VERSION VERSION_EQUAL 4.7))
message(FATAL_ERROR "${PROJECT_NAME} requires g++ 4.7 or greater.")
endif ()
elseif ("${CMAKE_CXX_COMPILER_ID}" MATCHES "Clang")
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -stdlib=libc++")
else ()
message(FATAL_ERROR "Your C++ compiler does not support C++11.")
endif ()
endif()
set(OpenCL_FOUND TRUE) include_directories(${CMAKE_CURRENT_BINARY_DIR})
set(OpenCL_INCLUDE_DIRS /usr/include/CL) include_directories(${OpenCL_INCLUDE_DIRS}})
set(OpenCL_LIBRARIES -lOpenCL) include_directories(..)
add_library(${EXECUTABLE} ${SRC_LIST} ${HEADERS})
TARGET_LINK_LIBRARIES(${EXECUTABLE} ${OpenCL_LIBRARIES} ethash)
if (NOT OpenCL_FOUND) install( TARGETS ${EXECUTABLE} RUNTIME DESTINATION bin ARCHIVE DESTINATION lib LIBRARY DESTINATION lib )
find_package(OpenCL) install( FILES ${HEADERS} DESTINATION include/${EXECUTABLE} )
endif()
if (OpenCL_FOUND)
set(CMAKE_CXX_FLAGS "-std=c++11 -Wall -Wno-unknown-pragmas -Wextra -Werror -pedantic -fPIC ${CMAKE_CXX_FLAGS}")
include_directories(${OpenCL_INCLUDE_DIRS} ${CMAKE_CURRENT_BINARY_DIR})
include_directories(..)
add_library(${LIBRARY} ethash_cl_miner.cpp ethash_cl_miner.h cl.hpp)
TARGET_LINK_LIBRARIES(${LIBRARY} ${OpenCL_LIBRARIES} ethash)
endif()

38
libethash-cl/ethash_cl_miner.cpp

@ -57,6 +57,33 @@ ethash_cl_miner::ethash_cl_miner()
{ {
} }
std::string ethash_cl_miner::platform_info()
{
std::vector<cl::Platform> platforms;
cl::Platform::get(&platforms);
if (platforms.empty())
{
debugf("No OpenCL platforms found.\n");
return std::string();
}
// get GPU device of the default platform
std::vector<cl::Device> devices;
platforms[0].getDevices(CL_DEVICE_TYPE_ALL, &devices);
if (devices.empty())
{
debugf("No OpenCL devices found.\n");
return std::string();
}
// use default device
unsigned device_num = 0;
cl::Device& device = devices[device_num];
std::string device_version = device.getInfo<CL_DEVICE_VERSION>();
return "{ platform: '" + platforms[0].getInfo<CL_PLATFORM_NAME>() + "', device: '" + device.getInfo<CL_DEVICE_NAME>() + "', version: '" + device_version + "' }";
}
void ethash_cl_miner::finish() void ethash_cl_miner::finish()
{ {
if (m_queue()) if (m_queue())
@ -65,7 +92,7 @@ void ethash_cl_miner::finish()
} }
} }
bool ethash_cl_miner::init(ethash_params const& params, std::function<void(void*)> _fillDAG, unsigned workgroup_size) bool ethash_cl_miner::init(ethash_params const& params, std::function<void(void*)> _fillDAG, unsigned workgroup_size, unsigned _deviceId)
{ {
// store params // store params
m_params = params; m_params = params;
@ -92,8 +119,13 @@ bool ethash_cl_miner::init(ethash_params const& params, std::function<void(void*
} }
// use default device // use default device
unsigned device_num = 0; cl::Device& device = devices[std::min<unsigned>(_deviceId, devices.size() - 1)];
cl::Device& device = devices[device_num]; for (unsigned n = 0; n < devices.size(); ++n)
{
auto version = devices[n].getInfo<CL_DEVICE_VERSION>();
auto name = devices[n].getInfo<CL_DEVICE_NAME>();
fprintf(stderr, "%s %d: %s (%s)\n", n == _deviceId ? "USING " : " ", n, name.c_str(), version.c_str());
}
std::string device_version = device.getInfo<CL_DEVICE_VERSION>(); std::string device_version = device.getInfo<CL_DEVICE_VERSION>();
fprintf(stderr, "Using device: %s (%s)\n", device.getInfo<CL_DEVICE_NAME>().c_str(),device_version.c_str()); fprintf(stderr, "Using device: %s (%s)\n", device.getInfo<CL_DEVICE_NAME>().c_str(),device_version.c_str());

12
libethash-cl/ethash_cl_miner.h

@ -2,7 +2,16 @@
#define __CL_ENABLE_EXCEPTIONS #define __CL_ENABLE_EXCEPTIONS
#define CL_USE_DEPRECATED_OPENCL_2_0_APIS #define CL_USE_DEPRECATED_OPENCL_2_0_APIS
#if defined(__clang__)
#pragma clang diagnostic push
#pragma clang diagnostic ignored "-Wunused-parameter"
#include "cl.hpp"
#pragma clang diagnostic pop
#else
#include "cl.hpp" #include "cl.hpp"
#endif
#include <time.h> #include <time.h>
#include <functional> #include <functional>
#include <libethash/ethash.h> #include <libethash/ethash.h>
@ -22,7 +31,8 @@ public:
public: public:
ethash_cl_miner(); ethash_cl_miner();
bool init(ethash_params const& params, std::function<void(void*)> _fillDAG, unsigned workgroup_size = 64); bool init(ethash_params const& params, std::function<void(void*)> _fillDAG, unsigned workgroup_size = 64, unsigned _deviceId = 0);
static std::string platform_info();
void finish(); void finish();
void hash(uint8_t* ret, uint8_t const* header, uint64_t nonce, unsigned count); void hash(uint8_t* ret, uint8_t const* header, uint64_t nonce, unsigned count);

8
libethcore/CMakeLists.txt

@ -11,6 +11,9 @@ aux_source_directory(. SRC_LIST)
include_directories(BEFORE ..) include_directories(BEFORE ..)
include_directories(${Boost_INCLUDE_DIRS}) include_directories(${Boost_INCLUDE_DIRS})
if (CPUID_FOUND)
include_directories(${Cpuid_INCLUDE_DIRS})
endif ()
set(EXECUTABLE ethcore) set(EXECUTABLE ethcore)
@ -25,6 +28,11 @@ endif()
target_link_libraries(${EXECUTABLE} ethash) target_link_libraries(${EXECUTABLE} ethash)
target_link_libraries(${EXECUTABLE} devcrypto) target_link_libraries(${EXECUTABLE} devcrypto)
target_link_libraries(${EXECUTABLE} devcore) target_link_libraries(${EXECUTABLE} devcore)
target_link_libraries(${EXECUTABLE} ethash-cl)
if (CPUID_FOUND)
target_link_libraries(${EXECUTABLE} ${CPUID_LIBRARIES})
endif ()
install( TARGETS ${EXECUTABLE} RUNTIME DESTINATION bin ARCHIVE DESTINATION lib LIBRARY DESTINATION lib ) install( TARGETS ${EXECUTABLE} RUNTIME DESTINATION bin ARCHIVE DESTINATION lib LIBRARY DESTINATION lib )
install( FILES ${HEADERS} DESTINATION include/${EXECUTABLE} ) install( FILES ${HEADERS} DESTINATION include/${EXECUTABLE} )

66
libethcore/Ethash.cpp

@ -23,6 +23,7 @@
#include <boost/detail/endian.hpp> #include <boost/detail/endian.hpp>
#include <boost/filesystem.hpp> #include <boost/filesystem.hpp>
#include <boost/algorithm/string.hpp>
#include <chrono> #include <chrono>
#include <array> #include <array>
#include <thread> #include <thread>
@ -38,6 +39,10 @@
#if ETH_ETHASHCL || !ETH_TRUE #if ETH_ETHASHCL || !ETH_TRUE
#include <libethash-cl/ethash_cl_miner.h> #include <libethash-cl/ethash_cl_miner.h>
#endif #endif
#if ETH_CPUID || !ETH_TRUE
#define HAVE_STDINT_H
#include <libcpuid/libcpuid.h>
#endif
#include "BlockInfo.h" #include "BlockInfo.h"
#include "EthashAux.h" #include "EthashAux.h"
using namespace std; using namespace std;
@ -142,6 +147,58 @@ void Ethash::CPUMiner::workLoop()
} }
} }
static string jsonEncode(map<string, string> const& _m)
{
string ret = "{";
for (auto const& i: _m)
{
string k = boost::replace_all_copy(boost::replace_all_copy(i.first, "\\", "\\\\"), "'", "\\'");
string v = boost::replace_all_copy(boost::replace_all_copy(i.second, "\\", "\\\\"), "'", "\\'");
if (ret.size() > 1)
ret += ", ";
ret += "\"" + k + "\":\"" + v + "\"";
}
return ret + "}";
}
std::string Ethash::CPUMiner::platformInfo()
{
string baseline = toString(std::thread::hardware_concurrency()) + "-thread CPU";
#if ETH_CPUID || !ETH_TRUE
if (!cpuid_present())
return baseline;
struct cpu_raw_data_t raw;
struct cpu_id_t data;
if (cpuid_get_raw_data(&raw) < 0)
return baseline;
if (cpu_identify(&raw, &data) < 0)
return baseline;
map<string, string> m;
m["vendor"] = data.vendor_str;
m["codename"] = data.cpu_codename;
m["brand"] = data.brand_str;
m["L1 cache"] = toString(data.l1_data_cache);
m["L2 cache"] = toString(data.l2_cache);
m["L3 cache"] = toString(data.l3_cache);
m["cores"] = toString(data.num_cores);
m["threads"] = toString(data.num_logical_cpus);
m["clocknominal"] = toString(cpu_clock_by_os());
m["clocktested"] = toString(cpu_clock_measure(200, 0));
/*
printf(" MMX : %s\n", data.flags[CPU_FEATURE_MMX] ? "present" : "absent");
printf(" MMX-extended: %s\n", data.flags[CPU_FEATURE_MMXEXT] ? "present" : "absent");
printf(" SSE : %s\n", data.flags[CPU_FEATURE_SSE] ? "present" : "absent");
printf(" SSE2 : %s\n", data.flags[CPU_FEATURE_SSE2] ? "present" : "absent");
printf(" 3DNow! : %s\n", data.flags[CPU_FEATURE_3DNOW] ? "present" : "absent");
*/
return jsonEncode(m);
#else
return baseline;
#endif
}
#if ETH_ETHASHCL || !ETH_TRUE #if ETH_ETHASHCL || !ETH_TRUE
class EthashCLHook: public ethash_cl_miner::search_hook class EthashCLHook: public ethash_cl_miner::search_hook
@ -204,6 +261,8 @@ private:
Ethash::GPUMiner* m_owner = nullptr; Ethash::GPUMiner* m_owner = nullptr;
}; };
unsigned Ethash::GPUMiner::s_deviceId = 0;
Ethash::GPUMiner::GPUMiner(ConstructionInfo const& _ci): Ethash::GPUMiner::GPUMiner(ConstructionInfo const& _ci):
Miner(_ci), Miner(_ci),
m_hook(new EthashCLHook(this)) m_hook(new EthashCLHook(this))
@ -245,7 +304,7 @@ void Ethash::GPUMiner::workLoop()
auto p = EthashAux::params(m_minerSeed); auto p = EthashAux::params(m_minerSeed);
auto cb = [&](void* d) { EthashAux::full(m_minerSeed, bytesRef((byte*)d, p.full_size)); }; auto cb = [&](void* d) { EthashAux::full(m_minerSeed, bytesRef((byte*)d, p.full_size)); };
m_miner->init(p, cb, 32); m_miner->init(p, cb, 32, s_deviceId);
} }
uint64_t upper64OfBoundary = (uint64_t)(u64)((u256)w.boundary >> 192); uint64_t upper64OfBoundary = (uint64_t)(u64)((u256)w.boundary >> 192);
@ -258,6 +317,11 @@ void Ethash::GPUMiner::pause()
stopWorking(); stopWorking();
} }
std::string Ethash::GPUMiner::platformInfo()
{
return ethash_cl_miner::platform_info();
}
#endif #endif
} }

6
libethcore/Ethash.h

@ -85,6 +85,8 @@ public:
CPUMiner(ConstructionInfo const& _ci): Miner(_ci), Worker("miner" + toString(index())) {} CPUMiner(ConstructionInfo const& _ci): Miner(_ci), Worker("miner" + toString(index())) {}
static unsigned instances() { return std::thread::hardware_concurrency(); } static unsigned instances() { return std::thread::hardware_concurrency(); }
static std::string platformInfo();
static void setDefaultDevice(unsigned) {}
protected: protected:
void kickOff() override void kickOff() override
@ -97,6 +99,7 @@ public:
private: private:
void workLoop() override; void workLoop() override;
static unsigned s_deviceId;
}; };
#if ETH_ETHASHCL || !ETH_TRUE #if ETH_ETHASHCL || !ETH_TRUE
@ -109,6 +112,8 @@ public:
~GPUMiner(); ~GPUMiner();
static unsigned instances() { return 1; } static unsigned instances() { return 1; }
static std::string platformInfo();
static void setDefaultDevice(unsigned _id) { s_deviceId = _id; }
protected: protected:
void kickOff() override; void kickOff() override;
@ -124,6 +129,7 @@ public:
ethash_cl_miner* m_miner = nullptr; ethash_cl_miner* m_miner = nullptr;
h256 m_minerSeed; ///< Last seed in m_miner h256 m_minerSeed; ///< Last seed in m_miner
static unsigned s_deviceId;
}; };
#else #else
using GPUMiner = CPUMiner; using GPUMiner = CPUMiner;

7
libethcore/Miner.h

@ -42,13 +42,14 @@ struct MiningProgress
// MiningProgress& operator+=(MiningProgress const& _mp) { hashes += _mp.hashes; ms = std::max(ms, _mp.ms); return *this; } // MiningProgress& operator+=(MiningProgress const& _mp) { hashes += _mp.hashes; ms = std::max(ms, _mp.ms); return *this; }
uint64_t hashes = 0; ///< Total number of hashes computed. uint64_t hashes = 0; ///< Total number of hashes computed.
uint64_t ms = 0; ///< Total number of milliseconds of mining thus far. uint64_t ms = 0; ///< Total number of milliseconds of mining thus far.
uint64_t rate() const { return hashes * 1000 / ms; }
}; };
struct MineInfo: public MiningProgress {}; struct MineInfo: public MiningProgress {};
inline std::ostream& operator<<(std::ostream& _out, MiningProgress _p) inline std::ostream& operator<<(std::ostream& _out, MiningProgress _p)
{ {
_out << (_p.hashes * 1000 / _p.ms) << "H/s = " << _p.hashes << " hashes / " << (double(_p.ms) / 1000) << "s"; _out << _p.rate() << " H/s = " << _p.hashes << " hashes / " << (double(_p.ms) / 1000) << " s";
return _out; return _out;
} }
@ -112,7 +113,9 @@ public:
m_hashCount = 0; m_hashCount = 0;
} }
uint64_t hashCount() { return m_hashCount; } uint64_t hashCount() const { return m_hashCount; }
void resetHashCount() { m_hashCount = 0; }
unsigned index() const { return m_index; } unsigned index() const { return m_index; }

1
libethereum/CMakeLists.txt

@ -36,7 +36,6 @@ target_link_libraries(${EXECUTABLE} ${Boost_REGEX_LIBRARIES})
target_link_libraries(${EXECUTABLE} secp256k1) target_link_libraries(${EXECUTABLE} secp256k1)
if (ETHASHCL) if (ETHASHCL)
target_link_libraries(${EXECUTABLE} ethash-cl) target_link_libraries(${EXECUTABLE} ethash-cl)
target_link_libraries(${EXECUTABLE} OpenCL)
endif () endif ()
if (CMAKE_COMPILER_IS_MINGW) if (CMAKE_COMPILER_IS_MINGW)

11
libethereum/Farm.h

@ -118,6 +118,17 @@ public:
return m_progress; return m_progress;
} }
/**
* @brief Reset the mining progess counter.
*/
void resetMiningProgress()
{
ETH_READ_GUARDED(x_minerWork)
for (auto const& i: m_miners)
i->resetHashCount();
resetTimer();
}
using SolutionFound = std::function<bool(Solution const&)>; using SolutionFound = std::function<bool(Solution const&)>;
/** /**

17
mix/qml/StateDialog.qml

@ -22,6 +22,8 @@ Dialog {
property alias isDefault: defaultCheckBox.checked property alias isDefault: defaultCheckBox.checked
property alias model: transactionsModel property alias model: transactionsModel
property alias transactionDialog: transactionDialog property alias transactionDialog: transactionDialog
property alias minerComboBox: comboMiner
property alias newAccAction: newAccountAction
property int stateIndex property int stateIndex
property var stateTransactions: [] property var stateTransactions: []
property var stateAccounts: [] property var stateAccounts: []
@ -46,12 +48,11 @@ Dialog {
accountsModel.clear(); accountsModel.clear();
stateAccounts = []; stateAccounts = [];
var miner = 0; var miner = 0;
for (var k = 0; k < item.accounts.length; k++) for (var k = 0; k < item.accounts.length; k++)
{ {
accountsModel.append(item.accounts[k]); accountsModel.append(item.accounts[k]);
stateAccounts.push(item.accounts[k]); stateAccounts.push(item.accounts[k]);
if (item.accounts[k].name === item.miner.name) if (item.miner && item.accounts[k].name === item.miner.name)
miner = k; miner = k;
} }
@ -91,6 +92,7 @@ Dialog {
} }
return item; return item;
} }
contentItem: Rectangle { contentItem: Rectangle {
color: stateDialogStyle.generic.backgroundColor color: stateDialogStyle.generic.backgroundColor
Rectangle { Rectangle {
@ -138,6 +140,7 @@ Dialog {
Button Button
{ {
id: newAccountButton
anchors.top: accountsLabel.bottom anchors.top: accountsLabel.bottom
anchors.topMargin: 10 anchors.topMargin: 10
iconSource: "qrc:/qml/img/plus.png" iconSource: "qrc:/qml/img/plus.png"
@ -148,10 +151,16 @@ Dialog {
id: newAccountAction id: newAccountAction
tooltip: qsTr("Add new Account") tooltip: qsTr("Add new Account")
onTriggered: onTriggered:
{
add();
}
function add()
{ {
var account = stateListModel.newAccount("1000000", QEther.Ether); var account = stateListModel.newAccount("1000000", QEther.Ether);
stateAccounts.push(account); stateAccounts.push(account);
accountsModel.append(account); accountsModel.append(account);
return account;
} }
} }
} }
@ -194,8 +203,12 @@ Dialog {
alertAlreadyUsed.open(); alertAlreadyUsed.open();
else else
{ {
if (stateAccounts[styleData.row].name === comboMiner.currentText)
comboMiner.currentIndex = 0;
stateAccounts.splice(styleData.row, 1); stateAccounts.splice(styleData.row, 1);
accountsModel.remove(styleData.row); accountsModel.remove(styleData.row);
comboMiner.model = stateAccounts;
comboMiner.update();
} }
} }
} }

4
mix/qml/StateListModel.qml

@ -193,7 +193,9 @@ Item {
accounts: [] accounts: []
}; };
item.accounts.push(newAccount("1000000", QEther.Ether, defaultAccount)); var account = newAccount("1000000", QEther.Ether, defaultAccount)
item.accounts.push(account);
item.miner = account;
//add all stdc contracts //add all stdc contracts
for (var i = 0; i < contractLibrary.model.count; i++) { for (var i = 0; i < contractLibrary.model.count; i++) {

3
mix/test/qml/TestMain.qml

@ -4,6 +4,7 @@ import org.ethereum.qml.TestService 1.0
import "../../qml" import "../../qml"
import "js/TestDebugger.js" as TestDebugger import "js/TestDebugger.js" as TestDebugger
import "js/TestTutorial.js" as TestTutorial import "js/TestTutorial.js" as TestTutorial
import "js/TestMiner.js" as TestMiner
import "js/TestProject.js" as TestProject import "js/TestProject.js" as TestProject
TestCase TestCase
@ -75,6 +76,8 @@ TestCase
function test_dbg_transactionWithParameter() { TestDebugger.test_transactionWithParameter(); } function test_dbg_transactionWithParameter() { TestDebugger.test_transactionWithParameter(); }
function test_dbg_constructorParameters() { TestDebugger.test_constructorParameters(); } function test_dbg_constructorParameters() { TestDebugger.test_constructorParameters(); }
function test_dbg_arrayParametersAndStorage() { TestDebugger.test_arrayParametersAndStorage(); } function test_dbg_arrayParametersAndStorage() { TestDebugger.test_arrayParametersAndStorage(); }
function test_miner_getDefaultiner() { TestMiner.test_getDefaultMiner(); }
function test_miner_selectMiner() { TestMiner.test_selectMiner(); }
function test_project_contractRename() { TestProject.test_contractRename(); } function test_project_contractRename() { TestProject.test_contractRename(); }
} }

20
mix/test/qml/js/TestMiner.js

@ -0,0 +1,20 @@
function test_getDefaultMiner()
{
newProject();
var state = mainApplication.projectModel.stateListModel.get(0);
compare(state.miner.secret, "cb73d9408c4720e230387d956eb0f829d8a4dd2c1055f96257167e14e7169074");
}
function test_selectMiner()
{
newProject();
mainApplication.projectModel.stateListModel.editState(0);
var account = mainApplication.projectModel.stateDialog.newAccAction.add();
account = mainApplication.projectModel.stateDialog.newAccAction.add();
mainApplication.projectModel.stateDialog.minerComboBox.currentIndex = 2;
ts.waitForRendering(mainApplication.projectModel.stateDialog.minerComboBox, 3000);
mainApplication.projectModel.stateDialog.acceptAndClose();
var state = mainApplication.projectModel.stateListModel.get(0);
compare(state.miner.secret, account.secret);
}
Loading…
Cancel
Save