├── .gitignore ├── LICENSE ├── Makefile ├── Makefile.config.template ├── README.md ├── accrdd ├── .gitignore ├── build │ └── mvn ├── pom.xml └── src │ └── main │ ├── java │ └── org │ │ └── apache │ │ └── spark │ │ └── blaze │ │ ├── .gitignore │ │ └── DataTransmitter.java │ └── scala │ └── org │ └── apache │ └── spark │ └── blaze │ ├── AccMapPartitionsRDD.scala │ ├── AccRDD.scala │ ├── Accelerator.scala │ ├── BlazeBroadcast.scala │ ├── BlazeMemoryFileHandler.scala │ ├── BlazeRuntime.scala │ ├── BlockInfo.scala │ ├── ShellRDD.scala │ ├── TestSampler.scala │ └── Util.scala ├── common ├── Makefile ├── acc_conf.proto ├── msgGamNam.proto ├── python │ └── .gitignore └── task.proto ├── examples ├── .gitignore ├── arrayTest │ ├── app │ │ ├── pom.xml │ │ ├── run-local.sh.template │ │ └── src │ │ │ └── main │ │ │ └── scala │ │ │ └── fcs_runtime │ │ │ └── examples │ │ │ └── ArrayTest.scala │ ├── cpp_app │ │ ├── .gitignore │ │ ├── Makefile │ │ └── main.cpp │ ├── cpu_task │ │ ├── ArrayTest.cpp │ │ └── Makefile │ └── gpu_task │ │ ├── .gitignore │ │ ├── ArrayTest.cl │ │ ├── ArrayTest.cpp │ │ └── Makefile ├── loopback │ ├── aal_task │ │ ├── conf.prototxt │ │ └── src │ │ │ ├── Makefile │ │ │ ├── NLB.cpp │ │ │ └── NLBApp.h │ └── app │ │ ├── pom.xml │ │ ├── run-local.sh.template │ │ └── src │ │ └── main │ │ └── scala │ │ └── LoopBack │ │ └── LoopBack.scala └── pi │ ├── app │ ├── .gitignore │ ├── Makefile │ ├── map.cpp │ ├── map.sh │ ├── reduce.cpp │ ├── reduce.sh │ └── run.sh │ └── cpu_task │ ├── Makefile │ ├── Pi.cpp │ └── conf ├── functional-test ├── arraytest │ ├── acc_task │ │ ├── ArrayTest.cpp │ │ └── Makefile │ ├── app │ │ ├── .gitignore │ │ ├── pom.xml │ │ ├── run.sh.template │ │ └── src │ │ │ └── main │ │ │ └── scala │ │ │ └── testapp │ │ │ └── ArrayTest.scala │ ├── client │ │ ├── Makefile │ │ └── main.cpp │ └── ocl_task │ │ ├── ArrayTest.cl │ │ ├── ArrayTest.cpp │ │ └── Makefile ├── conf.prototxt ├── masktest │ ├── acc_task │ │ ├── Makefile │ │ └── MaskTest.cpp │ └── app │ │ ├── pom.xml │ │ └── src │ │ └── main │ │ └── scala │ │ └── testapp │ │ └── MaskTest.scala └── tuple2test │ ├── acc_task │ ├── Makefile │ └── Tuple2Test.cpp │ └── app │ ├── pom.xml │ └── src │ └── main │ └── scala │ └── testapp │ └── Tuple2Test.scala ├── manager ├── bin │ └── .gitignore ├── include │ └── blaze │ │ ├── AccAgent.h │ │ ├── Admin.h │ │ ├── BlazeTest.h │ │ ├── Block.h │ │ ├── BlockManager.h │ │ ├── Client.h │ │ ├── CommManager.h │ │ ├── Common.h │ │ ├── Platform.h │ │ ├── PlatformManager.h │ │ ├── QueueManager.h │ │ ├── Task.h │ │ ├── TaskEnv.h │ │ ├── TaskManager.h │ │ ├── TaskQueue.h │ │ ├── main.h │ │ └── proto │ │ ├── acc_conf.pb.h │ │ ├── msgGamNam.pb.h │ │ └── task.pb.h ├── lib │ └── .gitignore ├── src │ ├── .gitignore │ ├── AccAgent.cpp │ ├── Admin.cpp │ ├── AppCommManager.cpp │ ├── Block.cpp │ ├── BlockManager.cpp │ ├── Client.cpp │ ├── CommManager.cpp │ ├── Common.cpp │ ├── GAMCommManager.cpp │ ├── Makefile │ ├── Platform.cpp │ ├── PlatformManager.cpp │ ├── QueueManager.cpp │ ├── Task.cpp │ ├── TaskEnv.cpp │ ├── TaskManager.cpp │ ├── admin.cpp │ ├── main.cpp │ └── proto │ │ └── .gitignore └── test │ ├── .gitignore │ ├── Makefile │ ├── bin │ └── .gitignore │ ├── common.mk │ ├── logs │ └── .gitignore │ ├── python │ ├── .gitignore │ ├── blaze_client.py │ ├── delete.py │ ├── register.py │ └── task_pb2.py │ ├── src │ ├── AppClients.cpp │ ├── BlockTests.cpp │ ├── ClientTests.cpp │ ├── ConfigTests.cpp │ ├── TestCommon.h │ └── main.cpp │ └── tasks │ ├── Makefile │ └── cpu │ ├── Makefile │ ├── arrayTest │ ├── Makefile │ └── arrayTest.cpp │ ├── common.mk │ ├── delay │ ├── Makefile │ └── delay.cpp │ └── loopBack │ ├── Makefile │ └── loopBack.cpp ├── platforms ├── Makefile ├── intel_aal │ ├── .gitignore │ ├── AALBlock.cpp │ ├── AALBlock.h │ ├── AALEnv.h │ ├── AALPlatform.cpp │ ├── AALPlatform.h │ ├── Makefile │ ├── RuntimeClient.cpp │ └── RuntimeClient.h └── nv_opencl │ ├── .gitignore │ ├── Makefile │ ├── include │ └── blaze │ │ └── nv_opencl │ │ ├── OpenCLBlock.h │ │ ├── OpenCLCommon.h │ │ ├── OpenCLEnv.h │ │ ├── OpenCLPlatform.h │ │ └── OpenCLQueueManager.h │ └── src │ ├── OpenCLBlock.cpp │ ├── OpenCLPlatform.cpp │ ├── OpenCLQueueManager.cpp │ └── OpenCLTaskEnv.cpp └── setup.sh /.gitignore: -------------------------------------------------------------------------------- 1 | *.log 2 | *.o 3 | *.so 4 | *.err 5 | target 6 | Makefile.config 7 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | COPYRIGHT 2 | 3 | All contributions by the University of California: 4 | Copyright (c) 2015, The Regents of the University of California (Regents) 5 | All rights reserved. 6 | 7 | All other contributions: 8 | Copyright (c) 2015, the respective contributors 9 | All rights reserved. 10 | 11 | Blaze uses a shared copyright model: each contributor holds copyright over 12 | their contributions to Blaze. The project versioning records all such 13 | contribution and copyright details. If a contributor wants to further mark 14 | their specific copyright on a particular contribution, they should indicate 15 | their copyright solely in the commit message of the change when it is 16 | committed. 17 | 18 | LICENSE 19 | 20 | Redistribution and use in source and binary forms, with or without 21 | modification, are permitted provided that the following conditions are met: 22 | 23 | 1. Redistributions of source code must retain the above copyright notice, this 24 | list of conditions and the following disclaimer. 25 | 2. Redistributions in binary form must reproduce the above copyright notice, 26 | this list of conditions and the following disclaimer in the documentation 27 | and/or other materials provided with the distribution. 28 | 29 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND 30 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 31 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 32 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR 33 | ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 34 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 35 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND 36 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 37 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 38 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 39 | 40 | CONTRIBUTION AGREEMENT 41 | 42 | By contributing to the UCLA-VAST/blaze repository through pull-request, comment, 43 | or otherwise, the contributor releases their content to the 44 | license and copyright terms herein. 45 | -------------------------------------------------------------------------------- /Makefile: -------------------------------------------------------------------------------- 1 | all: common accrdd nam 2 | 3 | common: 4 | make -C ./common 5 | 6 | accrdd: common 7 | cd accrdd; mvn package; mvn install 8 | 9 | nam: common 10 | make -C ./manager/src 11 | make -C ./platforms 12 | 13 | examples: 14 | make -C examples 15 | 16 | .PHONY: all common accrdd nam examples 17 | -------------------------------------------------------------------------------- /Makefile.config.template: -------------------------------------------------------------------------------- 1 | BOOST_DIR= 2 | PROTOBUF_DIR= 3 | GLOG_DIR= 4 | GFLAGS_DIR= 5 | GTEST_DIR= 6 | CUDA_DIR= 7 | ALTERA_OPENCL_DIR= 8 | ALTERA_OPENCL_BSP_DIR= 9 | 10 | CC=gcc 11 | PP=g++ 12 | AR=ar 13 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Blaze: Deploying Accelerators at Datacenter Scale 2 | ### Description 3 | Blaze is an accelerator-aware programming framework for warehouse-scale accelerator deployment. Blaze provides a programming interface that is compatible to Spark, an in-memory compute engine for large-scale data processing, and a runtime system that provides transparent accelerator management. With Blaze, the deployment effort of accelerator task is reduced by more than 10x compared to traditional frameworks such as OpenCL. Blaze is designed to efficiently manage accelerator platforms with intelligent data caching and task pipelining schemes to minimize the communication and data movement overheads. 4 | 5 | ### License 6 | The Blaze runtime system is released under [BSD 2-Clause license](https://github.com/BVLC/caffe/blob/master/LICENSE). 7 | The Blaze runtime system includes the following components: 8 | 9 | * AccRDD: A Spark extension including interface between Spark program and accelerators 10 | * manager: A accelerator manager that controls all local accelerators including context setup, data transfer and task execution 11 | 12 | In addition, each accelerator task is compiled with Blaze APIs. Some simple examples are provided in the `./examples` folder, which are released without restriction. 13 | 14 | ### Installing Blaze 15 | 0. **Prerequisites** 16 | 0. Boost (tested with 1.55.0) 17 | 0. Google Protobuf (tested with 2.5.0) 18 | 0. Apache Spark (tested with 1.3.1) 19 | 0. Apache Hadoop (tested with 2.5.2) 20 | 0. **Compiling** 21 | 0. Edit Makefile.config 22 | 0. `export BLAZE_HOME=$PWD/accrdd` 23 | 0. run `make` 24 | 25 | ### Running Loopback example 26 | 0. **Prerequisites** 27 | 0. Intel AALSDK 4.1.7 28 | 0. Intel AAL NLB example RTL 29 | 0. **Compiling** 30 | 0. From root directory run `make examples` 31 | 0. **Execution** 32 | 0. Start NLB ASE 33 | 0. On terminal 1 start Manager: `./manager/bin/acc_manager ./examples/loopback/acc_task/conf.prototxt` 34 | 0. On terminal 2 tart Spark program: `./examples/loopback/app/run.sh` or `./examples/loopback/app/run_local.sh` 35 | 36 | ### Contacts 37 | For any question or discussion, please contact the authors: 38 | 39 | * Di Wu: allwu@cs.ucla.edu 40 | * Hao Yu (Cody): hyu@cs.ucla.edu 41 | -------------------------------------------------------------------------------- /accrdd/.gitignore: -------------------------------------------------------------------------------- 1 | target 2 | -------------------------------------------------------------------------------- /accrdd/build/mvn: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env bash 2 | 3 | # Determine the current working directory 4 | _DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )" 5 | # Preserve the calling directory 6 | _CALLING_DIR="$(pwd)" 7 | # Options used during compilation 8 | _COMPILE_JVM_OPTS="-Xmx2g -XX:MaxPermSize=512M -XX:ReservedCodeCacheSize=512m" 9 | 10 | # Installs any application tarball given a URL, the expected tarball name, 11 | # and, optionally, a checkable binary path to determine if the binary has 12 | # already been installed 13 | ## Arg1 - URL 14 | ## Arg2 - Tarball Name 15 | ## Arg3 - Checkable Binary 16 | install_app() { 17 | local remote_tarball="$1/$2" 18 | local local_tarball="${_DIR}/$2" 19 | local binary="${_DIR}/$3" 20 | 21 | # setup `curl` and `wget` silent options if we're running on Jenkins 22 | local curl_opts="-L" 23 | local wget_opts="" 24 | if [ -n "$AMPLAB_JENKINS" ]; then 25 | curl_opts="-s ${curl_opts}" 26 | wget_opts="--quiet ${wget_opts}" 27 | else 28 | curl_opts="--progress-bar ${curl_opts}" 29 | wget_opts="--progress=bar:force ${wget_opts}" 30 | fi 31 | 32 | if [ -z "$3" -o ! -f "$binary" ]; then 33 | # check if we already have the tarball 34 | # check if we have curl installed 35 | # download application 36 | [ ! -f "${local_tarball}" ] && [ $(command -v curl) ] && \ 37 | echo "exec: curl ${curl_opts} ${remote_tarball}" && \ 38 | curl ${curl_opts} "${remote_tarball}" > "${local_tarball}" 39 | # if the file still doesn't exist, lets try `wget` and cross our fingers 40 | [ ! -f "${local_tarball}" ] && [ $(command -v wget) ] && \ 41 | echo "exec: wget ${wget_opts} ${remote_tarball}" && \ 42 | wget ${wget_opts} -O "${local_tarball}" "${remote_tarball}" 43 | # if both were unsuccessful, exit 44 | [ ! -f "${local_tarball}" ] && \ 45 | echo -n "ERROR: Cannot download $2 with cURL or wget; " && \ 46 | echo "please install manually and try again." && \ 47 | exit 2 48 | cd "${_DIR}" && tar -xzf "$2" 49 | rm -rf "$local_tarball" 50 | fi 51 | } 52 | 53 | # Install maven under the build/ folder 54 | install_mvn() { 55 | install_app \ 56 | "http://archive.apache.org/dist/maven/maven-3/3.2.5/binaries" \ 57 | "apache-maven-3.2.5-bin.tar.gz" \ 58 | "apache-maven-3.2.5/bin/mvn" 59 | MVN_BIN="${_DIR}/apache-maven-3.2.5/bin/mvn" 60 | } 61 | 62 | # Install zinc under the build/ folder 63 | install_zinc() { 64 | local zinc_path="zinc-0.3.5.3/bin/zinc" 65 | [ ! -f "${zinc_path}" ] && ZINC_INSTALL_FLAG=1 66 | install_app \ 67 | "http://downloads.typesafe.com/zinc/0.3.5.3" \ 68 | "zinc-0.3.5.3.tgz" \ 69 | "${zinc_path}" 70 | ZINC_BIN="${_DIR}/${zinc_path}" 71 | } 72 | 73 | # Determine the Scala version from the root pom.xml file, set the Scala URL, 74 | # and, with that, download the specific version of Scala necessary under 75 | # the build/ folder 76 | install_scala() { 77 | # determine the Scala version used in Spark 78 | local scala_version=`grep "scala.version" "${_DIR}/../pom.xml" | \ 79 | head -1 | cut -f2 -d'>' | cut -f1 -d'<'` 80 | local scala_bin="${_DIR}/scala-${scala_version}/bin/scala" 81 | 82 | install_app \ 83 | "http://downloads.typesafe.com/scala/${scala_version}" \ 84 | "scala-${scala_version}.tgz" \ 85 | "scala-${scala_version}/bin/scala" 86 | 87 | SCALA_COMPILER="$(cd "$(dirname ${scala_bin})/../lib" && pwd)/scala-compiler.jar" 88 | SCALA_LIBRARY="$(cd "$(dirname ${scala_bin})/../lib" && pwd)/scala-library.jar" 89 | } 90 | 91 | # Determines if a given application is already installed. If not, will attempt 92 | # to install 93 | ## Arg1 - application name 94 | ## Arg2 - Alternate path to local install under build/ dir 95 | check_and_install_app() { 96 | # create the local environment variable in uppercase 97 | local app_bin="`echo $1 | awk '{print toupper(\$0)}'`_BIN" 98 | # some black magic to set the generated app variable (i.e. MVN_BIN) into the 99 | # environment 100 | eval "${app_bin}=`which $1 2>/dev/null`" 101 | 102 | if [ -z "`which $1 2>/dev/null`" ]; then 103 | install_$1 104 | fi 105 | } 106 | 107 | # Setup healthy defaults for the Zinc port if none were provided from 108 | # the environment 109 | ZINC_PORT=${ZINC_PORT:-"3030"} 110 | 111 | # Check and install all applications necessary to build Spark 112 | check_and_install_app "mvn" 113 | 114 | # Install the proper version of Scala and Zinc for the build 115 | install_zinc 116 | install_scala 117 | 118 | # Reset the current working directory 119 | cd "${_CALLING_DIR}" 120 | 121 | # Now that zinc is ensured to be installed, check its status and, if its 122 | # not running or just installed, start it 123 | if [ -n "${ZINC_INSTALL_FLAG}" -o -z "`${ZINC_BIN} -status`" ]; then 124 | export ZINC_OPTS=${ZINC_OPTS:-"$_COMPILE_JVM_OPTS"} 125 | ${ZINC_BIN} -shutdown 126 | ${ZINC_BIN} -start -port ${ZINC_PORT} \ 127 | -scala-compiler "${SCALA_COMPILER}" \ 128 | -scala-library "${SCALA_LIBRARY}" &>/dev/null 129 | fi 130 | 131 | # Set any `mvn` options if not already present 132 | export MAVEN_OPTS=${MAVEN_OPTS:-"$_COMPILE_JVM_OPTS"} 133 | 134 | # Last, call the `mvn` command as usual 135 | ${MVN_BIN} "$@" 136 | -------------------------------------------------------------------------------- /accrdd/pom.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4.0.0 4 | 5 | org.apache.spark 6 | blaze_2.10 7 | 1.0.1 8 | jar 9 | 10 | 11 | UTF-8 12 | 1.7 13 | 2.10.4 14 | 2.10 15 | 16 | 17 | 18 | 19 | 20 | org.scala-tools 21 | maven-scala-plugin 22 | 23 | 24 | 25 | compile 26 | 27 | compile 28 | 29 | compile 30 | 31 | 32 | test-compile 33 | 34 | testCompile 35 | 36 | test-compile 37 | 38 | 39 | process-resources 40 | 41 | compile 42 | 43 | 44 | 45 | 46 | 47 | maven-compiler-plugin 48 | 49 | 1.5 50 | 1.5 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | org.scala-lang 59 | scala-library 60 | ${scala.version} 61 | 62 | 63 | junit 64 | junit 65 | 4.11 66 | test 67 | 68 | 69 | org.scalacheck 70 | scalacheck_${scala.version.tools} 71 | 1.12.0 72 | test 73 | 74 | 75 | org.scalatest 76 | scalatest_${scala.version.tools} 77 | 2.2.4 78 | test 79 | 80 | 81 | org.apache.spark 82 | spark-core_${scala.version.tools} 83 | 2.1.0 84 | 85 | 86 | com.google.protobuf 87 | protobuf-java 88 | 2.5.0 89 | 90 | 91 | 92 | -------------------------------------------------------------------------------- /accrdd/src/main/java/org/apache/spark/blaze/.gitignore: -------------------------------------------------------------------------------- 1 | AccMessage.java 2 | -------------------------------------------------------------------------------- /accrdd/src/main/scala/org/apache/spark/blaze/AccMapPartitionsRDD.scala: -------------------------------------------------------------------------------- 1 | package org.apache.spark.blaze 2 | 3 | import java.io._ 4 | import java.util.ArrayList 5 | import java.nio.ByteBuffer 6 | import java.nio.ByteOrder 7 | 8 | import scala.reflect.{ClassTag, classTag} 9 | import scala.reflect.runtime.universe._ 10 | import scala.collection.mutable._ 11 | 12 | import org.apache.spark._ 13 | import org.apache.spark.{Partition, TaskContext} 14 | import org.apache.spark.rdd._ 15 | import org.apache.spark.storage._ 16 | import org.apache.spark.scheduler._ 17 | import org.apache.spark.util.random.RandomSampler 18 | import org.apache.spark.internal.Logging 19 | /** 20 | * A RDD that uses accelerator to accelerate the computation. The behavior of AccMapPartitionsRDD is 21 | * similar to Spark MapPartitionsRDD which performs the computation for a whole partition at a 22 | * time. AccMapPartitionsRDD also processes a partition to reduce the communication overhead. 23 | * 24 | * @param appId The unique application ID of Spark. 25 | * @param prev The original RDD of Spark. 26 | * @param acc The developer extended accelerator class. 27 | */ 28 | class AccMapPartitionsRDD[U: ClassTag, T: ClassTag]( 29 | appId: String, 30 | prev: RDD[T], 31 | acc: Accelerator[T, U], 32 | port: Int, 33 | sampler: RandomSampler[Int, Int] 34 | ) extends AccRDD[U, T](appId, prev, acc, port, sampler) with Logging { 35 | 36 | /** 37 | * In case of failing to execute the computation on accelerator, 38 | * Blaze will execute the computation on JVM instead to guarantee the 39 | * functionality correctness, even the overhead of failing to execute 40 | * on accelerator is quite large. 41 | * 42 | * @param split The partition to be executed on JVM. 43 | * @param context TaskContext of Spark. 44 | * @return The output array 45 | */ 46 | override def computeOnJTP(split: Partition, context: TaskContext, partitionMask: Array[Byte]): Iterator[U] = { 47 | logInfo("Compute partition " + split.index + " using CPU") 48 | val input: Iterator[T] = firstParent[T].iterator(split, context) 49 | 50 | if (partitionMask != null) { // Sampled dataset 51 | val sampledInput = new Iterator[T] { 52 | val inputAry = input.toArray 53 | var sampledList = List[T]() 54 | var idx = 0 55 | while (idx < inputAry.length) { 56 | if (partitionMask(idx) != 0) 57 | sampledList = sampledList :+ inputAry(idx) 58 | idx += 1 59 | } 60 | idx = 0 61 | 62 | def hasNext : Boolean = { 63 | idx < sampledList.length 64 | } 65 | 66 | def next : T = { 67 | idx += 1 68 | sampledList(idx - 1) 69 | } 70 | } 71 | acc.call(sampledInput) 72 | } 73 | else { 74 | logWarning("Partition " + split.index + " has no mask") 75 | acc.call(input) 76 | } 77 | } 78 | } 79 | 80 | -------------------------------------------------------------------------------- /accrdd/src/main/scala/org/apache/spark/blaze/Accelerator.scala: -------------------------------------------------------------------------------- 1 | package org.apache.spark.blaze 2 | 3 | /** 4 | * An accelerator interface. Accelerator interface allows the developer to 5 | * extend and assign the hardware accelerator to accelerate the function. 6 | * The value `id` is used to assign the accelerator which should be provided 7 | * by accelerator manager. In addition, in case of unavailable accelerators, 8 | * the developer also has to create a software implementation, `call` method, 9 | * with the same functionality as the accelerator. 10 | * 11 | * @tparam T Type of accelerator input. Only allow primitive types and 1-D array. 12 | * @tparam U Type of accelerator output. Only allow primitive types and 1-D array. 13 | */ 14 | trait Accelerator[T, U] extends java.io.Serializable { 15 | 16 | /** The corresponding accelerator ID of the hardware accelerator. 17 | * The developer should consult the manager for the correct ID to use it. 18 | **/ 19 | val id: String 20 | 21 | /** The developer should specify the reference variables as arguments of extended 22 | * Accelerator class. This method is used for mapping from the class arguments to 23 | * the order in the hardware accelerator. For example: 24 | * 25 | * {{{ 26 | * class MyAccelerator(ref1: BlazeBroadcast[Array[Int]], ref2: BlazeBroadcast[Int]) 27 | * extends Accelerator[Array[Int], Int] { 28 | * def getArg(idx: Int): Option[BlazeBroadcast[_]] = { 29 | * if (idx == 0) Some(ref1) 30 | * else if (idx == 1) Some(ref2) 31 | * else None 32 | * } 33 | * } 34 | * }}} 35 | * 36 | * In this case, the protocol of hardware accelerator kernel would be: 37 | * 38 | * {{{ 39 | * void acc(int *input, int *ref1, int ref2) 40 | * }}} 41 | * 42 | * @param idx The index of each variable. 43 | * @return The corresponding variable within Some. Return None if 44 | * the index is out of range. 45 | **/ 46 | def getArg(idx: Int): Option[_] 47 | 48 | /** Report the total number of reference (broadcast) variables. 49 | * @return The total number of reference variables. 50 | **/ 51 | def getArgNum(): Int 52 | 53 | /** The content of the function in Scala which has the same functionality as 54 | * the hardware accelerator. This method is used when accelerator is not available. 55 | * 56 | * @param in An element of the input. 57 | * @return A corresponding element of the output. 58 | **/ 59 | def call(in: T): U = in.asInstanceOf[U] 60 | 61 | def call(in: Iterator[T]): Iterator[U] = in.asInstanceOf[Iterator[U]] 62 | } 63 | -------------------------------------------------------------------------------- /accrdd/src/main/scala/org/apache/spark/blaze/BlazeBroadcast.scala: -------------------------------------------------------------------------------- 1 | package org.apache.spark.blaze 2 | 3 | import java.io._ 4 | 5 | import org.apache.spark.broadcast.Broadcast 6 | import org.apache.spark.SparkException 7 | import org.apache.spark.internal.Logging 8 | import org.apache.spark.util.Utils 9 | 10 | import scala.reflect.ClassTag 11 | 12 | /** 13 | * A BlazeBroadcast variable. A BlazeBroadcast variable wraps a Spark broadcast variable with 14 | * an unique broadcast ID within the application. BlazeBroadcast variables will be broadcast 15 | * to the Blaze manager lazily and cached until the application has been terminated. 16 | * 17 | * @tparam T Type of broadcast data. 18 | */ 19 | class BlazeBroadcast[T: ClassTag](appId: String, bd: Broadcast[T]) extends java.io.Serializable { 20 | def getIntId() = Math 21 | .abs(("""\d+""".r findAllIn appId) 22 | .addString(new StringBuilder).toLong.toInt) 23 | 24 | var brdcst_id: Long = Util.getBlockID(getIntId(), bd.id.asInstanceOf[Int]) 25 | lazy val data = bd.value 26 | var length: Int = 0 27 | var size: Int = 0 28 | } 29 | -------------------------------------------------------------------------------- /accrdd/src/main/scala/org/apache/spark/blaze/BlazeRuntime.scala: -------------------------------------------------------------------------------- 1 | package org.apache.spark.blaze 2 | 3 | import java.io._ 4 | import scala.util.matching.Regex 5 | import scala.reflect.ClassTag 6 | 7 | import org.apache.spark._ 8 | import org.apache.spark.{Partition, TaskContext} 9 | import org.apache.spark.rdd._ 10 | import org.apache.spark.storage._ 11 | import org.apache.spark.scheduler._ 12 | import org.apache.spark.broadcast._ 13 | import org.apache.spark.internal.Logging 14 | 15 | /** 16 | * The entry point of Blaze runtime system. BlazeRuntime is mainly used for 17 | * wrapping RDD and broadcast variables, and maintaining the broadcast data list 18 | * for releasing. 19 | * 20 | * @param sc Spark context. 21 | */ 22 | class BlazeRuntime(sc: SparkContext) extends Logging { 23 | // get Logger object 24 | 25 | // The application signature generated based on Spark application ID. 26 | val appSignature: String = sc.applicationId 27 | 28 | var accPort: Int = 1027 29 | 30 | // Configure the port for AccManager 31 | def setAccPort(port: Int) = { 32 | accPort = port 33 | } 34 | 35 | var BroadcastList: List[BlazeBroadcast[_]] = List() 36 | 37 | /** 38 | * This method should be called by the developer at the end of the application 39 | * to release all broadcast blocks from Blaze manager and shutdown the SparkContext. 40 | * Ignore this method causes useless broadcast blocks occupy Blaze manager scratch memory. 41 | */ 42 | def stop() = { 43 | if (BroadcastList.length == 0) 44 | logInfo("No broadcast block to be released") 45 | else { 46 | // FIXME: Currently we use the fixed port number (1027) for all managers 47 | val WorkerList: Array[(String, Int)] = (sc.getExecutorStorageStatus) 48 | .map(w => w.blockManagerId.host) 49 | .distinct 50 | .map(w => (w, accPort)) 51 | 52 | logInfo("Releasing broadcast blocks from workers (" + WorkerList.length + "): " + 53 | WorkerList.map(w => w._1).mkString(", ")) 54 | 55 | val msg = DataTransmitter.buildMessage(appSignature, AccMessage.MsgType.ACCTERM) 56 | 57 | for (e <- BroadcastList) { 58 | DataTransmitter.addBroadcastData(msg, e.brdcst_id) 59 | logInfo("Broadcast block to be released: " + e.brdcst_id) 60 | } 61 | 62 | for (worker <- WorkerList) { 63 | try { 64 | val workerIP = Util.getIPByHostName(worker._1) 65 | if (!workerIP.isDefined) 66 | throw new RuntimeException("Cannot resolve host name " + worker._1) 67 | val transmitter = new DataTransmitter(workerIP.get, worker._2) 68 | transmitter.send(msg) 69 | val revMsg = transmitter.receive() 70 | if (revMsg.getType() == AccMessage.MsgType.ACCFINISH) 71 | logInfo("Successfully release " + BroadcastList.length + " broadcast blocks from Manager " + worker._1) 72 | else 73 | logInfo("Fail to release broadcast blocks from Manager " + worker._1) 74 | } 75 | catch { 76 | case e: Throwable => 77 | val sw = new StringWriter 78 | logInfo("Fail to release broadcast data from Manager " + worker._1 + ": " + sw.toString) 79 | } 80 | } 81 | } 82 | // do not shutdown SparkContext here since BlazeRuntime does not construct 83 | // a SparkContext 84 | // sc.stop 85 | // logInfo("Application " + appSignature + " shutdown.") 86 | } 87 | 88 | /** 89 | * Wrap a Spark RDD in a ShellRDD of Blaze. 90 | */ 91 | def wrap[T: ClassTag](rdd : RDD[T]) : ShellRDD[T] = { 92 | new ShellRDD[T](appSignature, rdd, accPort) 93 | } 94 | 95 | /** 96 | * Wrap a Spark broadcast in a BlazeBroadcast. 97 | */ 98 | def wrap[T: ClassTag](bd : Broadcast[T]) : BlazeBroadcast[T] = { 99 | val newBrdcst = new BlazeBroadcast[T](appSignature, bd) 100 | BroadcastList = BroadcastList :+ newBrdcst 101 | newBrdcst 102 | } 103 | } 104 | 105 | -------------------------------------------------------------------------------- /accrdd/src/main/scala/org/apache/spark/blaze/BlockInfo.scala: -------------------------------------------------------------------------------- 1 | package org.apache.spark.blaze 2 | 3 | import java.io._ 4 | 5 | import org.apache.spark.internal.Logging 6 | import org.apache.spark.util.Utils 7 | 8 | import scala.reflect.ClassTag 9 | 10 | /** 11 | * 12 | */ 13 | class BlockInfo { 14 | var id: Long = 0 15 | var numElt: Int = -1 16 | var eltLength: Int = -1 17 | var eltSize: Int = -1 18 | var fileName: String = null 19 | var fileSize: Int = 0 20 | var offset: Int = 0 21 | } 22 | -------------------------------------------------------------------------------- /accrdd/src/main/scala/org/apache/spark/blaze/ShellRDD.scala: -------------------------------------------------------------------------------- 1 | package org.apache.spark.blaze 2 | 3 | import scala.reflect.ClassTag 4 | import scala.reflect.runtime.universe._ 5 | import scala.collection.mutable._ 6 | 7 | import org.apache.spark._ 8 | import org.apache.spark.{Partition, TaskContext} 9 | import org.apache.spark.rdd._ 10 | import org.apache.spark.storage._ 11 | import org.apache.spark.scheduler._ 12 | import org.apache.spark.util.random._ 13 | 14 | /** 15 | * ShellRDD is only used for wrapping a Spark RDD. It returns a AccRDD 16 | * if the developer decides to execute the computation on the accelerator 17 | * by calling `map_acc` method. 18 | * 19 | * @param appId The application ID. 20 | * @param prev The original Spark RDD. 21 | */ 22 | class ShellRDD[T: ClassTag]( 23 | appId: String, 24 | prev: RDD[T], 25 | port: Int, 26 | sampler: RandomSampler[Int, Int] 27 | ) extends RDD[T](prev) { 28 | 29 | def this(id: String, prev: RDD[T], port: Int) = this(id, prev, port, null) 30 | 31 | override def getPartitions: Array[Partition] = firstParent[T].partitions 32 | 33 | // do nothing 34 | override def compute(split: Partition, context: TaskContext) = { 35 | val iter = new Iterator[T] { 36 | val nested = firstParent[T].iterator(split, context) 37 | 38 | def hasNext : Boolean = { 39 | nested.hasNext 40 | } 41 | 42 | def next : T = { 43 | nested.next 44 | } 45 | } 46 | iter 47 | } 48 | 49 | def map_acc[U: ClassTag](clazz: Accelerator[T, U]): AccRDD[U, T] = { 50 | new AccRDD(appId, this, clazz, port, sampler) 51 | } 52 | 53 | def sample_acc ( 54 | withReplacement: Boolean, 55 | fraction: Double, 56 | seed: Long = Util.random.nextLong): ShellRDD[T] = { 57 | require(fraction >= 0.0, "Negative fraction value: " + fraction) 58 | 59 | var thisSampler: RandomSampler[Int, Int] = null 60 | 61 | if (withReplacement) 62 | thisSampler = new PoissonSampler[Int](fraction) 63 | else 64 | thisSampler = new BernoulliSampler[Int](fraction) 65 | thisSampler.setSeed(seed) 66 | 67 | //if (seed == 904401792) { // Test mode 68 | // thisSampler = new TestSampler[Int] 69 | //} 70 | 71 | new ShellRDD(appId, this, port, thisSampler) 72 | } 73 | 74 | def mapPartitions_acc[U: ClassTag](clazz: Accelerator[T, U]): AccMapPartitionsRDD[U, T] = { 75 | new AccMapPartitionsRDD(appId, this, clazz, port, sampler) 76 | } 77 | } 78 | 79 | -------------------------------------------------------------------------------- /accrdd/src/main/scala/org/apache/spark/blaze/TestSampler.scala: -------------------------------------------------------------------------------- 1 | package org.apache.spark.blaze 2 | 3 | import scala.reflect.ClassTag 4 | import scala.reflect.runtime.universe._ 5 | import scala.collection.mutable._ 6 | 7 | import org.apache.spark._ 8 | import org.apache.spark.{Partition, TaskContext} 9 | import org.apache.spark.rdd._ 10 | import org.apache.spark.util.random._ 11 | 12 | abstract class TestSampler[T] extends RandomSampler[T, T] { 13 | 14 | override def setSeed(r: Long) = {} 15 | 16 | override def sample(items: Iterator[T]): Iterator[T] = { 17 | var out: List[T] = List() 18 | val N: Int = 30 19 | var idx: Int = 0 20 | 21 | while (items.hasNext) { 22 | val v: T = items.next 23 | if (idx < N) 24 | out = out :+ v 25 | idx += 1 26 | } 27 | out.iterator 28 | } 29 | 30 | //override def clone = new TestSampler[T] 31 | } 32 | -------------------------------------------------------------------------------- /common/Makefile: -------------------------------------------------------------------------------- 1 | include ../Makefile.config 2 | 3 | ifeq ($(PROTOBUF_DIR),) 4 | $(error PROTOBUF_DIR not set properly in Makefile.config) 5 | endif 6 | 7 | JAVA_OUT=../accrdd/src/main/java 8 | CPP_OUT=../manager/src/proto 9 | PYTHON_OUT=./python 10 | 11 | all: task.proto acc_conf.proto msgGamNam.proto 12 | $(PROTOBUF_DIR)/bin/protoc --cpp_out=$(CPP_OUT) --java_out=$(JAVA_OUT) --python_out=$(PYTHON_OUT) task.proto 13 | $(PROTOBUF_DIR)/bin/protoc --cpp_out=$(CPP_OUT) --python_out=$(PYTHON_OUT) acc_conf.proto 14 | $(PROTOBUF_DIR)/bin/protoc --cpp_out=$(CPP_OUT) msgGamNam.proto 15 | -------------------------------------------------------------------------------- /common/acc_conf.proto: -------------------------------------------------------------------------------- 1 | package blaze; 2 | 3 | enum AccType { 4 | CPU = 0; 5 | OpenCL = 1; 6 | CUDA = 2; 7 | ZYNQ = 3; 8 | } 9 | 10 | message AccPlatform { 11 | message KeyValue { 12 | required string key = 1; 13 | required string value = 2; 14 | } 15 | 16 | optional string id = 1 [default = "cpu"]; 17 | optional string path = 2 [default = ""]; 18 | optional string cache_loc = 3 [default = "cpu"]; 19 | optional int32 cache_limit = 4 [default = 16]; 20 | optional int32 scratch_limit = 5 [default = 4]; 21 | repeated KeyValue param = 6; 22 | repeated AccWorker acc = 7; 23 | } 24 | 25 | message AccWorker { 26 | message KeyValue { 27 | required string key = 1; 28 | required string value = 2; 29 | } 30 | 31 | required string id = 1; 32 | required string path = 2; 33 | repeated KeyValue param = 3; 34 | optional string kernel_name = 4; 35 | optional string kernel_path = 5; 36 | } 37 | 38 | message ManagerConf { 39 | optional int32 app_port = 1 [default = 1027]; 40 | optional int32 gam_port = 2 [default = 1028]; 41 | optional int32 verbose = 3 [default = 0]; 42 | optional string local_dir = 4 [default = "/tmp"]; 43 | repeated AccPlatform platform = 5; 44 | } 45 | -------------------------------------------------------------------------------- /common/msgGamNam.proto: -------------------------------------------------------------------------------- 1 | package blaze; 2 | 3 | option java_package = "org.apache.hadoop.fcs"; 4 | 5 | message Gam2NamRequest { 6 | enum MsgType { 7 | ACCNAMES = 0; 8 | SHARERATE = 1; 9 | } 10 | required MsgType type = 1; 11 | optional bool pull = 2 [default = false]; 12 | } 13 | 14 | message Accelerator { 15 | optional string acc_name = 1; 16 | optional string device_name = 2; 17 | } 18 | 19 | message Nam2GamAccNames { 20 | optional bool isUpdated = 1 [default = false]; 21 | repeated Accelerator acc_names = 2; 22 | } 23 | -------------------------------------------------------------------------------- /common/python/.gitignore: -------------------------------------------------------------------------------- 1 | # Ignore everything in this directory 2 | * 3 | # Except this file 4 | !.gitignore 5 | -------------------------------------------------------------------------------- /common/task.proto: -------------------------------------------------------------------------------- 1 | package blaze; 2 | 3 | option java_package = "org.apache.spark.blaze"; 4 | option java_outer_classname = "AccMessage"; 5 | 6 | enum MsgType { 7 | ACCREQUEST = 0; 8 | ACCGRANT = 1; 9 | ACCREJECT = 2; 10 | ACCFINISH = 3; 11 | ACCDATA = 4; 12 | ACCFAILURE = 5; 13 | ACCBROADCAST = 6; 14 | ACCTERM = 7; 15 | ACCREGISTER = 8; 16 | ACCDELETE = 9; 17 | } 18 | 19 | message DataMsg { 20 | optional int64 partition_id = 1; 21 | optional bool cached = 2; 22 | optional bool sampled = 3; 23 | optional int32 element_length = 4; 24 | optional int32 element_size = 5; 25 | optional int32 num_elements = 6; 26 | optional int64 scalar_value = 7; 27 | optional string file_path = 8; 28 | optional int64 file_size = 9; 29 | optional int64 file_offset = 10; 30 | optional string mask_path = 11; 31 | } 32 | 33 | message TaskMsg { 34 | required MsgType type = 1; 35 | optional string app_id = 2; 36 | optional string acc_id = 3; 37 | repeated DataMsg data = 4; 38 | optional AccMsg acc = 5; 39 | optional string msg = 6; 40 | } 41 | 42 | message AccMsg { 43 | message KeyValue { 44 | required string key = 1; 45 | required bytes value = 2; 46 | } 47 | required string acc_id = 1; 48 | required string platform_id = 2; 49 | optional bytes task_impl = 3; 50 | repeated KeyValue param = 4; 51 | } 52 | -------------------------------------------------------------------------------- /examples/.gitignore: -------------------------------------------------------------------------------- 1 | *.so 2 | *.o 3 | log 4 | -------------------------------------------------------------------------------- /examples/arrayTest/app/pom.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | fcs_runtime.example 4 | arraytest 5 | jar 6 | "ArrayTest" 7 | 1.0 8 | 4.0.0 9 | 10 | 11 | 12 | scala-tools.org 13 | Scala-tools Maven2 Repository 14 | http://scala-tools.org/repo-releases 15 | 16 | 17 | fcs-mvn.repo 18 | Falcon Computing Solutions Repository 19 | http://support.falcon-computing.com/mvn-repo 20 | 21 | 22 | 23 | 24 | 1.7 25 | 2.10.4 26 | 2.10 27 | 2.10 28 | 1.5.1 29 | UTF-8 30 | UTF-8 31 | 32 | 33 | 34 | 35 | scala-tools.org 36 | Scala-tools Maven2 Repository 37 | http://scala-tools.org/repo-releases 38 | 39 | 40 | 41 | 42 | 43 | org.scala-lang 44 | scala-library 45 | ${scala.version} 46 | 47 | 48 | org.apache.spark 49 | spark-core_${scala.binary.version} 50 | ${spark.version} 51 | 52 | 53 | org.apache.spark 54 | spark-mllib_${scala.binary.version} 55 | ${spark.version} 56 | 57 | 58 | org.apache.spark 59 | blaze_${scala.binary.version} 60 | 1.0 61 | 62 | 63 | 64 | 65 | 66 | 67 | org.scala-tools 68 | maven-scala-plugin 69 | 2.15.2 70 | 71 | 72 | 73 | compile 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | -------------------------------------------------------------------------------- /examples/arrayTest/app/run-local.sh.template: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | SPARK_HOME= 4 | $SPARK_HOME/spark-submit --class LoopBack \ 5 | --master local[*] \ 6 | target/LoopBack-0.0.0.jar $@ 7 | 8 | -------------------------------------------------------------------------------- /examples/arrayTest/app/src/main/scala/fcs_runtime/examples/ArrayTest.scala: -------------------------------------------------------------------------------- 1 | import Array._ 2 | import scala.math._ 3 | import scala.util.Random 4 | import java.net._ 5 | import org.apache.spark.rdd._ 6 | import org.apache.spark.SparkContext 7 | import org.apache.spark.SparkConf 8 | import org.apache.spark.blaze._ 9 | 10 | class ArrayTest(v: BlazeBroadcast[Array[Double]]) 11 | extends Accelerator[Array[Double], Array[Double]] { 12 | 13 | val id: String = "ArrayTest" 14 | 15 | def getArgNum(): Int = 1 16 | 17 | def getArg(idx: Int): Option[_] = { 18 | if (idx == 0) 19 | Some(v) 20 | else 21 | None 22 | } 23 | 24 | override def call(in: Array[Double]): Array[Double] = { 25 | (in, v.data).zipped.map(_ + _) 26 | } 27 | } 28 | 29 | object TestApp { 30 | def main(args : Array[String]) { 31 | 32 | val conf = new SparkConf() 33 | conf.setAppName("TestApp") 34 | 35 | val sc = new SparkContext(conf) 36 | val acc = new BlazeRuntime(sc) 37 | 38 | var num_sample = 32 39 | var num_part = 4 40 | 41 | if (args.size == 2) { 42 | num_sample = args(0).toInt 43 | num_part = args(1).toInt 44 | } 45 | 46 | val data = Array.fill(num_sample)(Array.fill(8)(Random.nextDouble)); 47 | val offset = Array.fill(8)(Random.nextDouble); 48 | 49 | val rdd = sc.parallelize(data, num_part) 50 | val rdd_acc = acc.wrap(rdd) 51 | 52 | val bc_data = sc.broadcast(offset) 53 | val bc_data_acc = acc.wrap(bc_data) 54 | 55 | val res_acc = rdd_acc.map_acc(new ArrayTest(bc_data_acc)).collect 56 | val res_cpu = rdd.map(e => (e, bc_data.value).zipped.map(_ + _)).collect 57 | 58 | // compare results 59 | if (res_acc.deep != res_cpu.deep) 60 | { 61 | println("Result incorrect") 62 | println("map result: \n" + res_cpu.deep.mkString("\n")) 63 | println("map_acc results: \n" + res_acc.deep.mkString("\n")) 64 | } 65 | else { 66 | println("result correct") 67 | } 68 | acc.stop() 69 | } 70 | } 71 | 72 | -------------------------------------------------------------------------------- /examples/arrayTest/cpp_app/.gitignore: -------------------------------------------------------------------------------- 1 | app 2 | -------------------------------------------------------------------------------- /examples/arrayTest/cpp_app/Makefile: -------------------------------------------------------------------------------- 1 | MANAGER_DIR=../../../manager 2 | include ../../../Makefile.config 3 | 4 | # check all variables 5 | ifeq ($(BOOST_DIR),) 6 | $(error BOOST_DIR not set properly in Makefile.config) 7 | endif 8 | ifeq ($(PROTOBUF_DIR),) 9 | $(error PROTOBUF_DIR not set properly in Makefile.config) 10 | endif 11 | ifeq ($(GLOG_DIR),) 12 | $(error GLOG_DIR not set properly in Makefile.config) 13 | endif 14 | 15 | PP=g++ 16 | CC=gcc 17 | 18 | CFLAGS := -shared -fPIC -std=c++0x -m64 -g 19 | 20 | COMPILE := $(CFLAGS) \ 21 | -I$(MANAGER_DIR)/include \ 22 | -I$(BOOST_DIR)/include \ 23 | -I$(PROTOBUF_DIR)/include \ 24 | -I$(GFLAGS_DIR)/include \ 25 | -I$(GLOG_DIR)/include 26 | 27 | LINK := -L$(MANAGER_DIR)/lib -lblaze \ 28 | -L$(BOOST_DIR)/lib \ 29 | -lboost_system -lboost_thread -lboost_iostreams -lboost_filesystem -lboost_regex \ 30 | -L$(PROTOBUF_DIR)/lib -lprotobuf \ 31 | -L$(GLOG_DIR)/lib -lglog \ 32 | -lpthread -lm -ldl 33 | 34 | all: app 35 | 36 | app: main.o 37 | $(PP) -o $@ main.o $(LINK) 38 | 39 | %.o: %.cpp 40 | $(PP) $(COMPILE) $< -o $@ 41 | 42 | clean: 43 | rm -rf *.o 44 | rm -rf app 45 | -------------------------------------------------------------------------------- /examples/arrayTest/cpp_app/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | #include "blaze/Client.h" 4 | 5 | using namespace blaze; 6 | 7 | class ArrayTestClient: public Client { 8 | public: 9 | ArrayTestClient(): Client("ArrayTest", 2, 1) {;} 10 | 11 | void compute() { 12 | int num_samples = getInputNumItems(0); 13 | int feature_size = getInputLength(1); 14 | 15 | double* data_ptr = (double*)getInputPtr(0); 16 | double* weight_ptr = (double*)getInputPtr(1); 17 | double* output_ptr = (double*)createOutput(0, 18 | num_samples, feature_size, sizeof(double)); 19 | 20 | for (int i = 0; i < num_samples; i++) { 21 | for (int j = 0; j < feature_size; j++) { 22 | output_ptr[i * feature_size + j] = 23 | data_ptr[i * feature_size +j] + 24 | weight_ptr[j]; 25 | } 26 | } 27 | } 28 | }; 29 | 30 | int main(int argc, char** argv) { 31 | 32 | // GLOG configuration 33 | google::InitGoogleLogging(argv[0]); 34 | FLAGS_logtostderr = 1; 35 | FLAGS_v = 2; 36 | 37 | if (argc < 2) { 38 | printf("USAGE: %s \n", argv[0]); 39 | return -1; 40 | } 41 | 42 | int num_samples = atoi(argv[1]); 43 | int feature_size = 1024; 44 | 45 | if (argc > 3) { 46 | feature_size = atoi(argv[2]); 47 | } 48 | int data_size = num_samples*feature_size; 49 | 50 | try { 51 | ArrayTestClient client; 52 | 53 | double* data_ptr = (double*)client.createInput(0, num_samples, feature_size, sizeof(double), BLAZE_INPUT); 54 | double* weight_ptr = (double*)client.createInput(1, feature_size, 1, sizeof(double), BLAZE_INPUT); 55 | 56 | double* output_base = new double[num_samples*feature_size]; 57 | 58 | // setup input with random data 59 | for (int i=0; i max_diff) { 88 | max_diff = diff; 89 | } 90 | 91 | diff_total += diff; 92 | if (output_base[k]!=0) { 93 | diff_ratio += diff / std::abs(output_base[k]); 94 | } 95 | 96 | if (diff / std::abs(output_base[k]) > 0.05 && 97 | k<10) 98 | { 99 | printf("%d: %f|%f, ratio=%f\n", 100 | k, 101 | output_base[k], 102 | output_ptr[k], 103 | diff/std::abs(output_base[k])); 104 | } 105 | } 106 | if (diff_total < 1e-6) { 107 | printf("Result correct\n"); 108 | } 109 | else { 110 | printf("Result incorrect\n"); 111 | } 112 | } 113 | catch (std::exception &e) { 114 | printf("%s\n", e.what()); 115 | return -1; 116 | } 117 | 118 | return 0; 119 | } 120 | -------------------------------------------------------------------------------- /examples/arrayTest/cpu_task/ArrayTest.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | #include "blaze/Task.h" 5 | 6 | using namespace blaze; 7 | 8 | class ArrayTest : public Task { 9 | public: 10 | 11 | // extends the base class constructor 12 | // to indicate how many input blocks 13 | // are required 14 | ArrayTest(): Task(2) {;} 15 | 16 | // overwrites the compute function 17 | virtual void compute() { 18 | 19 | // get input data dimensions 20 | int total_length = getInputLength(0); 21 | int num_vectors = getInputNumItems(0); 22 | int vector_length = total_length / num_vectors; 23 | 24 | // get the pointer to input/output data 25 | double* a = (double*)getInput(0); 26 | double* b = (double*)getInput(1); 27 | double* c = (double*)getOutput(0, 28 | vector_length, num_vectors, sizeof(double)); 29 | 30 | // perform computation 31 | // c[i] = a[i] + b 32 | for (int i=0; i 2 | 3 | #include "blaze/Task.h" 4 | #include "blaze/nv_opencl/OpenCLEnv.h" 5 | 6 | using namespace blaze; 7 | 8 | class ArrayTest : public Task { 9 | public: 10 | 11 | // extends the base class constructor 12 | // to indicate how many input blocks 13 | // are required 14 | ArrayTest(): Task(2) {;} 15 | 16 | // overwrites the compute function 17 | virtual void compute() { 18 | 19 | struct timeval t1, t2, tr; 20 | 21 | // dynamically cast the TaskEnv to OpenCLEnv 22 | OpenCLTaskEnv* ocl_env = (OpenCLTaskEnv*)getEnv(); 23 | 24 | // get input data length 25 | int total_length = getInputLength(0); 26 | int num_vectors = getInputNumItems(0); 27 | int vector_length = total_length / num_vectors; 28 | 29 | // get OpenCL context 30 | cl_context context = ocl_env->getContext(); 31 | cl_command_queue command = ocl_env->getCmdQueue(); 32 | cl_program program = ocl_env->getProgram(); 33 | 34 | int err; 35 | cl_event event; 36 | 37 | cl_kernel kernel = clCreateKernel(program, "arrayTest", &err); 38 | if (!kernel || err != CL_SUCCESS) { 39 | throw std::runtime_error( 40 | "Failed to create compute kernel arrayTest"); 41 | } 42 | 43 | // get the pointer to input/output data 44 | cl_mem ocl_a = *((cl_mem*)getInput(0)); 45 | cl_mem ocl_b = *((cl_mem*)getInput(1)); 46 | cl_mem ocl_c = *((cl_mem*)getOutput( 47 | 0, vector_length, num_vectors, 48 | sizeof(double))); 49 | 50 | if (!ocl_a || !ocl_b || !ocl_c) { 51 | throw std::runtime_error("Buffer are not allocated"); 52 | } 53 | 54 | // Set the arguments to our compute kernel 55 | err |= clSetKernelArg(kernel, 0, sizeof(int), &num_vectors); 56 | err |= clSetKernelArg(kernel, 1, sizeof(int), &vector_length); 57 | err |= clSetKernelArg(kernel, 2, sizeof(cl_mem), &ocl_a); 58 | err |= clSetKernelArg(kernel, 3, sizeof(cl_mem), &ocl_b); 59 | err |= clSetKernelArg(kernel, 4, sizeof(cl_mem), &ocl_c); 60 | if (err != CL_SUCCESS) { 61 | throw std::runtime_error("Cannot set kernel args\n"); 62 | } 63 | 64 | size_t work_lsize[1] = {128}; 65 | size_t work_gsize[1]; 66 | work_gsize[0] = 64*work_lsize[0]; 67 | 68 | err = clEnqueueNDRangeKernel(command, kernel, 1, NULL, work_gsize, work_lsize, 0, NULL, &event); 69 | clWaitForEvents(1, &event); 70 | } 71 | }; 72 | 73 | extern "C" Task* create() { 74 | return new ArrayTest(); 75 | } 76 | 77 | extern "C" void destroy(Task* p) { 78 | delete p; 79 | } 80 | -------------------------------------------------------------------------------- /examples/arrayTest/gpu_task/Makefile: -------------------------------------------------------------------------------- 1 | MANAGER_DIR=../../../manager 2 | include ../../../Makefile.config 3 | 4 | # check all variables 5 | ifeq ($(BOOST_DIR),) 6 | $(error BOOST_DIR not set properly in Makefile.config) 7 | endif 8 | ifeq ($(PROTOBUF_DIR),) 9 | $(error PROTOBUF_DIR not set properly in Makefile.config) 10 | endif 11 | ifeq ($(GLOG_DIR),) 12 | $(error GLOG_DIR not set properly in Makefile.config) 13 | endif 14 | ifeq ($(CUDA_DIR),) 15 | $(error CUDA_DIR not set properly in Makefile.config) 16 | endif 17 | 18 | CFLAGS := -shared -fPIC -std=c++0x -m64 19 | COMPILE := $(CFLAGS) \ 20 | -I$(MANAGER_DIR)/include \ 21 | -I$(MANAGER_DIR)/../platforms/nv_opencl/include \ 22 | -I$(BOOST_DIR)/include \ 23 | -I$(PROTOBUF_DIR)/include \ 24 | -I$(GLOG_DIR)/include \ 25 | -I$(GFLAGS_DIR)/include \ 26 | -I$(CUDA_DIR)/include 27 | 28 | LINK := -L$(CUDA_DIR)/lib64 -lOpenCL 29 | 30 | ACC := ArrayTest 31 | 32 | OBJS := $(addsuffix .so, $(ACC)) 33 | 34 | all: $(OBJS) 35 | 36 | %.so: %.cpp Makefile 37 | $(PP) $(COMPILE) $(LINK) $< -o $@ 38 | 39 | clean: 40 | rm -rf $(OBJS) 41 | -------------------------------------------------------------------------------- /examples/loopback/aal_task/conf.prototxt: -------------------------------------------------------------------------------- 1 | port : 1027 2 | verbose : 2 3 | platform : { 4 | type: CPU 5 | cache_limit: 16384 6 | scratch_limit: 4096 7 | acc : { 8 | id : "NLB" 9 | path : "examples/loopback/acc_task/libNLB.so" 10 | } 11 | } 12 | -------------------------------------------------------------------------------- /examples/loopback/aal_task/src/Makefile: -------------------------------------------------------------------------------- 1 | include ../../../../Makefile.config 2 | MANAGER_DIR=../../../../manager 3 | 4 | CPPFLAGS ?= 5 | CXX ?= g++ 6 | LDFLAGS ?= 7 | 8 | ifneq (,$(ndebug)) 9 | else 10 | CPPFLAGS += -DENABLE_DEBUG=1 11 | endif 12 | ifneq (,$(nassert)) 13 | else 14 | CPPFLAGS += -DENABLE_ASSERT=1 15 | endif 16 | 17 | CPPFLAGS += -fPIC -std=c++0x -m64 -g \ 18 | -I$(AAL_DIR)/include \ 19 | -I$(MANAGER_DIR)/include \ 20 | -I$(BOOST_DIR)/include \ 21 | -I$(PROTOBUF_DIR)/include 22 | 23 | LDFLAGS += -L$(AAL_DIR)/lib -Wl,-rpath-link \ 24 | -Wl,$(AAL_DIR)/lib -Wl,-rpath \ 25 | -Wl,$(AAL_DIR)/lib \ 26 | -L$(AAL_DIR)/lib64 -Wl,-rpath-link \ 27 | -Wl,$(AAL_DIR)/lib64 -Wl,-rpath \ 28 | -Wl,$(AAL_DIR)/lib64 29 | 30 | all: ../libNLB.so 31 | 32 | ../libNLB.so: NLB.o 33 | $(CXX) -g -shared -o $@ $< $(LDFLAGS) -lOSAL -lAAS -lxlrt 34 | 35 | NLB.o: NLB.cpp *.h Makefile 36 | $(CXX) $(CPPFLAGS) -D__AAL_USER__=1 -c -o $@ NLB.cpp 37 | 38 | clean: 39 | $(RM) ../libNLB.so *.o 40 | 41 | .PHONY:all clean 42 | -------------------------------------------------------------------------------- /examples/loopback/aal_task/src/NLB.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | #include 6 | #include 7 | #include 8 | #include 9 | 10 | #include "blaze.h" 11 | using namespace blaze; 12 | 13 | #include "NLBApp.h" 14 | 15 | class NLB : public Task { 16 | public: 17 | 18 | // extends the base class constructor 19 | // to indicate how many input blocks 20 | // are required 21 | NLB(): Task(1) {;} 22 | 23 | // overwrites the compute function 24 | virtual void compute() { 25 | 26 | // get input data length 27 | int data_length = getInputLength(0); 28 | 29 | if (data_length == 0 || 30 | data_length % 8 != 0) 31 | { 32 | throw std::runtime_error("Invalid data length"); 33 | } 34 | 35 | // get the pointer to input/output data 36 | int n_items = getInputNumItems(0); 37 | double* src_data = (double*)getInput(0); 38 | double* dst_data = (double*)getOutput( 39 | 0, data_length/n_items, n_items, 40 | sizeof(double)); 41 | 42 | printf("#items=%d, length=%d\n", n_items, data_length/n_items); 43 | 44 | if (!src_data || !dst_data) { 45 | throw std::runtime_error("Cannot get data pointers"); 46 | } 47 | 48 | RuntimeClient runtimeClient; 49 | if(!runtimeClient.isOK()){ 50 | throw std::runtime_error("Runtime Failed to Start"); 51 | } 52 | 53 | HelloCCINLBApp theApp( 54 | dst_data, src_data, 55 | data_length*sizeof(double), &runtimeClient); 56 | 57 | // start real computation 58 | theApp.run(); 59 | } 60 | }; 61 | 62 | extern "C" Task* create() { 63 | return new NLB(); 64 | } 65 | 66 | extern "C" void destroy(Task* p) { 67 | delete p; 68 | } 69 | -------------------------------------------------------------------------------- /examples/loopback/app/pom.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | LoopBack 4 | LoopBack 5 | jar 6 | "LoopBack" 7 | 4.0.0 8 | 0.0.0 9 | 10 | 11 | 12 | scala-tools.org 13 | Scala-tools Maven2 Repository 14 | http://scala-tools.org/repo-releases 15 | 16 | 17 | maven-hadoop 18 | Hadoop Releases 19 | https://repository.cloudera.com/content/repositories/releases/ 20 | 21 | 22 | cloudera-repos 23 | Cloudera Repos 24 | https://repository.cloudera.com/artifactory/cloudera-repos/ 25 | 26 | 27 | 28 | 29 | 30 | scala-tools.org 31 | Scala-tools Maven2 Repository 32 | http://scala-tools.org/repo-releases 33 | 34 | 35 | 36 | 37 | UTF-8 38 | UTF-8 39 | 1.7 40 | 2.10.4 41 | 2.10 42 | 2.10 43 | 1.5.1 44 | 2.6.0 45 | 1.0.1 46 | 47 | 48 | 49 | 50 | 51 | org.scala-tools 52 | maven-scala-plugin 53 | 2.15.2 54 | 55 | 56 | 57 | compile 58 | 59 | 60 | 61 | 62 | 63 | maven-compiler-plugin 64 | 3.1 65 | 66 | 1.6 67 | 1.6 68 | 69 | 70 | 71 | 72 | 73 | 74 | 75 | org.scala-lang 76 | scala-library 77 | ${scala.version} 78 | 79 | 80 | org.apache.spark 81 | spark-core_${scala.binary.version} 82 | ${spark.version} 83 | 84 | 85 | org.apache.spark 86 | blaze_${scala.binary.version} 87 | ${blaze.version} 88 | 89 | 90 | 91 | -------------------------------------------------------------------------------- /examples/loopback/app/run-local.sh.template: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | SPARK_HOME= 4 | $SPARK_HOME/spark-submit --class LoopBack \ 5 | --master local[*] \ 6 | target/LoopBack-0.0.0.jar $@ 7 | 8 | -------------------------------------------------------------------------------- /examples/loopback/app/src/main/scala/LoopBack/LoopBack.scala: -------------------------------------------------------------------------------- 1 | import org.apache.spark.SparkContext 2 | import org.apache.spark.SparkContext._ 3 | import org.apache.spark.SparkConf 4 | import Array._ 5 | import org.apache.spark.rdd._ 6 | 7 | import scala.math._ 8 | import java.util._ 9 | 10 | import org.apache.spark.blaze._ 11 | 12 | class LoopBack() 13 | extends Accelerator[Array[Double], Array[Double]] { 14 | 15 | val id: String = "LoopBack" 16 | def getArg(idx: Int): Option[BlazeBroadcast[_]] = None 17 | def getArgNum(): Int = 0 18 | 19 | override def call(data: Array[Double]): Array[Double] = { 20 | val out = new Array[Double](data.size) 21 | Array.copy(data, 0, out, 0, data.size) 22 | out 23 | } 24 | } 25 | 26 | object LoopBack { 27 | 28 | def genData( 29 | sc: SparkContext, 30 | n_elements: Int, 31 | n_parts: Int): RDD[Array[Double]] = { 32 | 33 | val data = sc.parallelize(0 until n_elements, n_parts).map{ idx => 34 | val rand = new Random(42 + idx) 35 | val x = Array.fill[Double](8) { rand.nextGaussian() } 36 | x 37 | } 38 | data 39 | } 40 | 41 | def main(args : Array[String]) { 42 | 43 | if (args.length != 2) { 44 | System.err.println("Usage: LoopBack <#elements> <#parts>") 45 | System.exit(1) 46 | } 47 | val sc = get_spark_context("LoopBack") 48 | val acc = new BlazeRuntime(sc) 49 | 50 | val n_elements = args(0).toInt 51 | val n_parts = args(1).toInt 52 | 53 | val data = acc.wrap(genData(sc, n_elements, n_parts)) 54 | 55 | val src = data.collect 56 | val dst = data.map_acc(new LoopBack).collect 57 | 58 | 59 | if (src.deep == dst.deep) { 60 | println("results correct") 61 | acc.stop() 62 | } 63 | else { 64 | println("results incorrect") 65 | println(src.deep.mkString("\n")) 66 | println(dst.deep.mkString("\n")) 67 | acc.stop() 68 | System.exit(1) 69 | } 70 | } 71 | 72 | def get_spark_context(appName : String) : SparkContext = { 73 | val conf = new SparkConf() 74 | conf.setAppName(appName) 75 | 76 | return new SparkContext(conf) 77 | } 78 | } 79 | 80 | -------------------------------------------------------------------------------- /examples/pi/app/.gitignore: -------------------------------------------------------------------------------- 1 | map-bin 2 | reduce-bin 3 | *.txt 4 | -------------------------------------------------------------------------------- /examples/pi/app/Makefile: -------------------------------------------------------------------------------- 1 | MANAGER_DIR=../../../manager 2 | include ../../../Makefile.config 3 | 4 | # check all variables 5 | ifeq ($(BOOST_DIR),) 6 | $(error BOOST_DIR not set properly in Makefile.config) 7 | endif 8 | ifeq ($(PROTOBUF_DIR),) 9 | $(error PROTOBUF_DIR not set properly in Makefile.config) 10 | endif 11 | ifeq ($(GLOG_DIR),) 12 | $(error GLOG_DIR not set properly in Makefile.config) 13 | endif 14 | 15 | PP=g++ 16 | CC=gcc 17 | AR=ar 18 | 19 | CFLAGS = -c -fPIC -std=c++0x -g 20 | COMPILE := $(CFLAGS) \ 21 | -I$(MANAGER_DIR)/include \ 22 | -I$(BOOST_DIR)/include \ 23 | -I$(PROTOBUF_DIR)/include \ 24 | -I$(GLOG_DIR)/include \ 25 | -I$(GFLAGS_DIR)/include 26 | 27 | LINK := -L$(MANAGER_DIR)/lib -lblaze \ 28 | -L$(BOOST_DIR)/lib \ 29 | -lboost_system -lboost_thread -lboost_iostreams -lboost_filesystem -lboost_regex \ 30 | -L$(PROTOBUF_DIR)/lib -lprotobuf \ 31 | -L$(GLOG_DIR)/lib -lglog \ 32 | -L$(GFLAGS_DIR)/lib -lgflags \ 33 | -lpthread -lm -ldl 34 | 35 | all: map-bin reduce-bin 36 | 37 | map-bin: map.o 38 | $(PP) -o $@ $< $(LINK) 39 | 40 | reduce-bin: reduce.o 41 | $(PP) -o $@ $< $(LINK) 42 | 43 | %.o: %.cpp Makefile 44 | $(PP) $(COMPILE) $< -o $@ 45 | 46 | clean: 47 | rm -rf *.o 48 | rm -rf map-bin 49 | rm -rf reduce-bin 50 | -------------------------------------------------------------------------------- /examples/pi/app/map.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | #include 6 | #include 7 | 8 | int main(int argc, char** argv) { 9 | 10 | srand(time(NULL)); 11 | 12 | for (std::string line; std::getline(std::cin, line); ) 13 | { 14 | printf("key\t%f,%f\n", 15 | (double)rand()/RAND_MAX, 16 | (double)rand()/RAND_MAX); 17 | } 18 | 19 | return 0; 20 | } 21 | -------------------------------------------------------------------------------- /examples/pi/app/map.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | source ../../../setup.sh 4 | ./map-bin $@ 5 | -------------------------------------------------------------------------------- /examples/pi/app/reduce.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | #include 6 | #include 7 | #include 8 | 9 | #include 10 | 11 | #include "blaze/Client.h" 12 | 13 | using namespace blaze; 14 | 15 | class PiClient: public Client { 16 | public: 17 | 18 | PiClient(): Client("Pi", 1, 1) {;} 19 | 20 | void compute() { 21 | int num_pairs = getInputNumItems(0); 22 | double* data_ptr = (double*)getInputPtr(0); 23 | uint32_t* output_ptr = (uint32_t*)createOutput(0, 24 | 2, 1, sizeof(uint32_t)); 25 | 26 | uint32_t inside_count = 0; 27 | uint32_t outside_count = 0; 28 | 29 | for (int i=0; i > all_data; 53 | for (std::string line; std::getline(std::cin, line); ) 54 | { 55 | std::stringstream ss(line); 56 | 57 | std::string key; 58 | std::string value; 59 | double x = 0; 60 | double y = 0; 61 | 62 | std::getline(ss, key, '\t'); 63 | 64 | try { 65 | std::getline(ss, value, ','); 66 | x = std::stof(value); 67 | std::getline(ss, value); 68 | y = std::stof(value); 69 | } catch (std::exception &e) { 70 | continue; 71 | } 72 | all_data.push_back(std::make_pair(x, y)); 73 | } 74 | 75 | // send to accelerator 76 | PiClient client; 77 | 78 | // prepare input data 79 | double* data_ptr = (double*)client.createInput(0, all_data.size(), 2, sizeof(double), BLAZE_INPUT); 80 | 81 | for (int i=0; i> $TMP_FILE 13 | hdfs dfs -copyFromLocal `pwd`/$TMP_FILE $WORK_DIR 14 | 15 | if [[ "$?" != "0" ]]; then 16 | echo "Task failed" 17 | exit 1 18 | fi 19 | 20 | $HADOOP_HOME/bin/hadoop jar $HADOOP_HOME/share/hadoop/tools/lib/hadoop-streaming-2.6.0.jar \ 21 | -files file:`pwd`/map-bin,file:`pwd`/reduce-bin,file:`pwd`/map.sh,file:`pwd`/reduce.sh \ 22 | -D mapreduce.label=cpu \ 23 | -input $WORK_DIR/$TMP_FILE \ 24 | -output $WORK_DIR/output_pi \ 25 | -mapper map.sh \ 26 | -reducer reduce.sh &> hadoop.log 27 | 28 | hdfs dfs -ls $WORK_DIR/output_pi/_SUCCESS &> /dev/null 29 | 30 | if [[ "$?" != "0" ]]; then 31 | echo "Task failed" 32 | else 33 | ret=`hdfs dfs -cat $WORK_DIR/output_pi/* | head -n 1 | cut -f2` 34 | pi=`echo 4*$ret/$N | bc -l` 35 | echo "PI is estimated to be: $pi" 36 | fi 37 | 38 | # clean up 39 | rm $TMP_FILE 40 | hdfs dfs -rm $WORK_DIR/$TMP_FILE &> /dev/null 41 | hdfs dfs -rm -r $WORK_DIR/output_pi &> /dev/null 42 | -------------------------------------------------------------------------------- /examples/pi/cpu_task/Makefile: -------------------------------------------------------------------------------- 1 | MANAGER_DIR=../../../manager 2 | include ../../../Makefile.config 3 | 4 | # check all variables 5 | ifeq ($(BOOST_DIR),) 6 | $(error BOOST_DIR not set properly in Makefile.config) 7 | endif 8 | ifeq ($(PROTOBUF_DIR),) 9 | $(error PROTOBUF_DIR not set properly in Makefile.config) 10 | endif 11 | ifeq ($(GLOG_DIR),) 12 | $(error GLOG_DIR not set properly in Makefile.config) 13 | endif 14 | 15 | PP=g++ 16 | CC=gcc 17 | 18 | CFLAGS := -shared -fPIC -std=c++0x -m64 19 | COMPILE := $(CFLAGS) \ 20 | -I$(MANAGER_DIR)/include \ 21 | -I$(BOOST_DIR)/include \ 22 | -I$(PROTOBUF_DIR)/include \ 23 | -I$(GLOG_DIR)/include \ 24 | -I$(GFLAGS_DIR)/include 25 | 26 | ACC = Pi 27 | 28 | OBJS= $(addsuffix .so, $(ACC)) 29 | 30 | all: $(OBJS) 31 | 32 | %.so: %.cpp Makefile 33 | $(PP) $(COMPILE) $< -o $@ 34 | 35 | clean: 36 | rm -rf $(OBJS) 37 | -------------------------------------------------------------------------------- /examples/pi/cpu_task/Pi.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | #include "blaze/Task.h" 6 | 7 | using namespace blaze; 8 | 9 | class Pi : public Task { 10 | public: 11 | 12 | // extends the base class constructor 13 | // to indicate how many input blocks 14 | // are required 15 | Pi(): Task(1) {;} 16 | 17 | // overwrites the compute function 18 | virtual void compute() { 19 | 20 | // get input data dimensions 21 | int num_data = getInputNumItems(0); 22 | 23 | // get the pointer to input/output data 24 | double* input = (double*)getInput(0); 25 | uint32_t* output = (uint32_t*)getOutput( 26 | 0, 1, 2, sizeof(uint32_t)); 27 | 28 | uint32_t inside_count = 0; 29 | uint32_t outside_count = 0; 30 | 31 | // perform computation 32 | for (int i=0; i 2 | #include 3 | 4 | #include "blaze.h" 5 | 6 | using namespace blaze; 7 | 8 | class ArrayTest : public Task { 9 | public: 10 | 11 | // extends the base class constructor 12 | // to indicate how many input blocks 13 | // are required 14 | ArrayTest(): Task(2) {;} 15 | 16 | // overwrites the compute function 17 | virtual void compute() { 18 | 19 | // get input data length 20 | int data_length = getInputLength(0); 21 | int num_samples = getInputNumItems(0); 22 | int item_length = data_length / num_samples; 23 | int weight_length = getInputLength(1); 24 | 25 | // get the pointer to input/output data 26 | double* a = (double*)getInput(0); 27 | double* val = (double*)getInput(1); 28 | double* b = (double*)getOutput(0, item_length, num_samples, sizeof(double)); 29 | 30 | // perform computation 31 | double val_sum = 0.0; 32 | for (int k = 0; k < weight_length; k++) { 33 | val_sum += val[k]; 34 | } 35 | 36 | for (int i = 0; i < num_samples; i++) { 37 | for (int j = 0; j < item_length; j++) { 38 | b[i * item_length + j] = a[i * item_length +j] + val_sum; 39 | } 40 | } 41 | // if there is any error, throw exceptions 42 | } 43 | }; 44 | 45 | extern "C" Task* create() { 46 | return new ArrayTest(); 47 | } 48 | 49 | extern "C" void destroy(Task* p) { 50 | delete p; 51 | } 52 | -------------------------------------------------------------------------------- /functional-test/arraytest/acc_task/Makefile: -------------------------------------------------------------------------------- 1 | MANAGER_DIR=../../../manager 2 | include ../../../Makefile.config 3 | 4 | # check all variables 5 | ifeq ($(BOOST_DIR),) 6 | $(error BOOST_DIR not set properly in Makefile.config) 7 | endif 8 | ifeq ($(PROTOBUF_DIR),) 9 | $(error PROTOBUF_DIR not set properly in Makefile.config) 10 | endif 11 | PP=g++ 12 | CC=gcc 13 | 14 | CFLAGS= -shared -fPIC -std=c++0x -m64 -g 15 | COMPILE= $(CFLAGS) \ 16 | -I$(MANAGER_DIR)/include \ 17 | -I$(BOOST_DIR)/include \ 18 | -I$(PROTOBUF_DIR)/include 19 | 20 | ACC = ArrayTest 21 | 22 | OBJS= $(addsuffix .so, $(addprefix ../, $(ACC))) 23 | 24 | all: $(OBJS) 25 | 26 | ../%.so: %.cpp Makefile 27 | $(PP) $(COMPILE) $< -o $@ 28 | 29 | clean: 30 | rm -rf $(OBJS) 31 | -------------------------------------------------------------------------------- /functional-test/arraytest/app/.gitignore: -------------------------------------------------------------------------------- 1 | *.sh 2 | -------------------------------------------------------------------------------- /functional-test/arraytest/app/pom.xml: -------------------------------------------------------------------------------- 1 | 2 | 16 | 17 | test 18 | test 19 | jar 20 | "ArrayTest" 21 | 4.0.0 22 | 0.0.0 23 | 24 | 25 | 26 | scala-tools.org 27 | Scala-tools Maven2 Repository 28 | http://scala-tools.org/repo-releases 29 | 30 | 31 | maven-hadoop 32 | Hadoop Releases 33 | https://repository.cloudera.com/content/repositories/releases/ 34 | 35 | 36 | cloudera-repos 37 | Cloudera Repos 38 | https://repository.cloudera.com/artifactory/cloudera-repos/ 39 | 40 | 41 | 42 | 43 | 44 | scala-tools.org 45 | Scala-tools Maven2 Repository 46 | http://scala-tools.org/repo-releases 47 | 48 | 49 | 50 | 51 | UTF-8 52 | UTF-8 53 | 54 | 55 | 56 | 57 | org.scala-lang 58 | scala-library 59 | 2.10.4 60 | 61 | 62 | org.apache.spark 63 | spark-core_2.10 64 | 1.5.1 65 | 66 | 67 | org.apache.spark 68 | blaze_2.10 69 | 1.0 70 | 71 | 72 | 73 | 74 | 75 | 76 | org.scala-tools 77 | maven-scala-plugin 78 | 2.15.2 79 | 80 | 81 | 82 | compile 83 | 84 | 85 | 86 | 87 | 88 | maven-compiler-plugin 89 | 3.1 90 | 91 | 1.6 92 | 1.6 93 | 94 | 95 | 96 | org.apache.maven.plugins 97 | maven-shade-plugin 98 | 2.3 99 | 100 | 101 | package 102 | 103 | shade 104 | 105 | 106 | 107 | 108 | org.apache.spark:blaze_2.10 109 | 110 | 111 | 112 | 113 | 114 | 115 | 116 | 117 | 118 | 119 | -------------------------------------------------------------------------------- /functional-test/arraytest/app/run.sh.template: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | SPARK_HOME= 4 | --driver-memory 8G \ 5 | --executor-memory 8G \ 6 | --master local[*] \ 7 | target/test-0.0.0.jar $@ 8 | 9 | -------------------------------------------------------------------------------- /functional-test/arraytest/app/src/main/scala/testapp/ArrayTest.scala: -------------------------------------------------------------------------------- 1 | import Array._ 2 | import scala.math._ 3 | import java.net._ 4 | import org.apache.spark.rdd._ 5 | import org.apache.spark.SparkContext 6 | import org.apache.spark.SparkContext._ 7 | import org.apache.spark.SparkConf 8 | import org.apache.spark.util.random._ 9 | import org.apache.spark.blaze._ 10 | 11 | class ArrayTest(v: BlazeBroadcast[Array[Double]]) 12 | extends Accelerator[Array[Double], Array[Double]] { 13 | 14 | val id: String = "ArrayTest" 15 | 16 | def getArgNum(): Int = 1 17 | 18 | def getArg(idx: Int): Option[_] = { 19 | if (idx == 0) 20 | Some(v) 21 | else 22 | None 23 | } 24 | 25 | override def call(in: Array[Double]): Array[Double] = { 26 | val ary = new Array[Double](in.length) 27 | val s = v.data.sum 28 | for (i <- 0 until in.length) { 29 | ary(i) = in(i) + s 30 | } 31 | ary 32 | } 33 | 34 | override def call(in: Iterator[Array[Double]]): Iterator[Array[Double]] = { 35 | val inAry = in.toArray 36 | val length: Int = inAry.length 37 | val itemLength: Int = inAry(0).length 38 | val outAry = new Array[Array[Double]](length) 39 | val s = v.data.sum 40 | 41 | for (i <- 0 until length) { 42 | outAry(i) = new Array[Double](itemLength) 43 | for (j <- 0 until itemLength) 44 | outAry(i)(j) = inAry(i)(j) + s 45 | } 46 | 47 | outAry.iterator 48 | } 49 | } 50 | 51 | object TestApp { 52 | def main(args : Array[String]) { 53 | 54 | val conf = new SparkConf() 55 | conf.setAppName("TestApp") 56 | 57 | val sc = new SparkContext(conf) 58 | val acc = new BlazeRuntime(sc) 59 | 60 | val v = Array(1.1, 2.2, 3.3) 61 | 62 | println("Functional test: array type AccRDD with array type broadcast value") 63 | 64 | val data = new Array[Array[Double]](256) 65 | for (i <- 0 until 256) { 66 | data(i) = new Array[Double](2).map(e => random) 67 | } 68 | val rdd = sc.parallelize(data, 256) 69 | 70 | val rdd_acc = acc.wrap(rdd) 71 | val brdcst_v = acc.wrap(sc.broadcast(v)) 72 | 73 | val res0 = rdd_acc.map_acc(new ArrayTest(brdcst_v)).collect 74 | val res1 = rdd_acc.mapPartitions_acc(new ArrayTest(brdcst_v)).collect 75 | val res2 = rdd.map(e => e.map(ee => ee + v.sum)).collect 76 | 77 | // compare results 78 | if (res0.deep != res1.deep || 79 | res1.deep != res2.deep || 80 | res0.deep != res2.deep) 81 | { 82 | println("input: \n" + data.deep.mkString("\n")) 83 | println("map result: \n" + res2.deep.mkString("\n")) 84 | println("map_acc results: \n" + res0.deep.mkString("\n")) 85 | println("mapParititions_acc results: \n" + res1.deep.mkString("\n")) 86 | } 87 | else { 88 | println("result correct") 89 | } 90 | acc.stop() 91 | } 92 | } 93 | 94 | -------------------------------------------------------------------------------- /functional-test/arraytest/client/Makefile: -------------------------------------------------------------------------------- 1 | MANAGER_DIR=../../../manager 2 | include ../../../Makefile.config 3 | 4 | # check all variables 5 | ifeq ($(BOOST_DIR),) 6 | $(error BOOST_DIR not set properly in Makefile.config) 7 | endif 8 | ifeq ($(PROTOBUF_DIR),) 9 | $(error PROTOBUF_DIR not set properly in Makefile.config) 10 | endif 11 | 12 | PP=g++ 13 | 14 | CFLAGS= -c -fPIC -std=c++0x -g 15 | COMPILE= $(CFLAGS) \ 16 | -I$(MANAGER_DIR)/src \ 17 | -I$(BOOST_DIR)/include \ 18 | -I$(PROTOBUF_DIR)/include 19 | 20 | LINK= -L$(MANAGER_DIR)/lib -lblaze \ 21 | -L$(BOOST_DIR)/lib \ 22 | -lboost_system -lboost_thread -lboost_iostreams -lboost_filesystem -lboost_regex \ 23 | -L$(PROTOBUF_DIR)/lib -lprotobuf \ 24 | -L$(GLOG_DIR)/lib -lglog \ 25 | -lpthread -lm -ldl 26 | 27 | all: app 28 | 29 | app: main.o 30 | $(PP) -o $@ main.o $(LINK) 31 | 32 | %.o: %.cpp Makefile 33 | $(PP) $(COMPILE) $< -o $@ 34 | 35 | clean: 36 | rm -rf *.o 37 | rm -rf app 38 | -------------------------------------------------------------------------------- /functional-test/arraytest/client/main.cpp: -------------------------------------------------------------------------------- 1 | 2 | #include "Client.h" 3 | 4 | #define LABEL_SIZE 10 5 | #define FEATURE_SIZE 784 6 | 7 | using namespace blaze; 8 | 9 | int main(int argc, char** argv) { 10 | 11 | if (argc < 2) { 12 | printf("USAGE: %s \n", argv[0]); 13 | return -1; 14 | } 15 | 16 | int num_samples = atoi(argv[1]); 17 | int feature_size = 1024; 18 | 19 | if (argc > 3) { 20 | feature_size = atoi(argv[2]); 21 | } 22 | int data_size = num_samples*feature_size; 23 | 24 | try { 25 | Client client("ArrayTest", "C++"); 26 | 27 | double* data_ptr = (double*)client.alloc(num_samples, feature_size, feature_size*sizeof(double), BLAZE_INPUT); 28 | double* weight_ptr = (double*)client.alloc(feature_size, 1, sizeof(double), BLAZE_INPUT); 29 | double* output_ptr = (double*)client.alloc(num_samples, feature_size, feature_size*sizeof(double), BLAZE_OUTPUT); 30 | 31 | double* output_base = new double[num_samples*feature_size]; 32 | 33 | // setup input with random data 34 | for (int i=0; i max_diff) { 62 | max_diff = diff; 63 | } 64 | 65 | diff_total += diff; 66 | if (output_base[k]!=0) { 67 | diff_ratio += diff / std::abs(output_base[k]); 68 | } 69 | 70 | if (diff / std::abs(output_base[k]) > 0.05) { 71 | printf("%d: %f|%f, ratio=%f\n", 72 | k, 73 | output_base[k], 74 | output_ptr[k], 75 | diff/std::abs(output_base[k])); 76 | } 77 | } 78 | if (diff_total < 1e-6) { 79 | printf("Result correct\n"); 80 | } 81 | else { 82 | printf("Result incorrect\n"); 83 | printf("diff: %f max, %f/point, %f%/point\n", 84 | max_diff, 85 | diff_total/(data_size+1), 86 | diff_ratio/(data_size+1)*100.0); 87 | } 88 | } 89 | catch (std::exception &e) { 90 | printf("%s\n", e.what()); 91 | return -1; 92 | } 93 | 94 | return 0; 95 | } 96 | -------------------------------------------------------------------------------- /functional-test/arraytest/ocl_task/ArrayTest.cl: -------------------------------------------------------------------------------- 1 | __kernel 2 | void arrayTest( 3 | int weight_length, 4 | int num_items, 5 | int item_length, 6 | __global double* val, 7 | __global double* a, 8 | __global double* b 9 | ) 10 | { 11 | int gid = get_group_id(0); 12 | int gdim = get_num_groups(0); 13 | 14 | int tid = get_local_id(0); 15 | int tdim = get_local_size(0); 16 | 17 | for (int i = gid; i < num_items; i+=gdim) { 18 | for (int j = tid; j < item_length; j+=tdim) { 19 | double val_sum = 0.0; 20 | for (int k = 0; k < weight_length; k++) { 21 | val_sum += val[k]; 22 | } 23 | b[i * item_length + j] = a[i * item_length +j] + val_sum; 24 | } 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /functional-test/arraytest/ocl_task/ArrayTest.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | #include 6 | #include 7 | #include 8 | #include 9 | 10 | #include "Task.h" 11 | #include "OpenCLEnv.h" 12 | 13 | using namespace blaze; 14 | 15 | class ArrayTest : public Task { 16 | public: 17 | 18 | // extends the base class constructor 19 | // to indicate how many input blocks 20 | // are required 21 | ArrayTest(): Task(2) {;} 22 | 23 | // overwrites the compute function 24 | // Input data: 25 | // - data: layout as num_samples x [double label, double[] feature] 26 | // - weight: (num_labels-1) x feature_length 27 | // Output data: 28 | // - gradient plus loss: [double[] gradient, double loss] 29 | virtual void compute() { 30 | 31 | struct timeval t1, t2, tr; 32 | 33 | try { 34 | // dynamically cast the TaskEnv to OpenCLEnv 35 | OpenCLTaskEnv* ocl_env = (OpenCLTaskEnv*)getEnv(); 36 | 37 | // get input data length 38 | int data_length = getInputLength(0); 39 | int num_samples = getInputNumItems(0); 40 | int weight_length = getInputLength(1); 41 | int item_length = data_length / num_samples; 42 | 43 | // get OpenCL context 44 | cl_context context = ocl_env->getContext(); 45 | cl_command_queue command = ocl_env->getCmdQueue(); 46 | cl_program program = ocl_env->getProgram(); 47 | 48 | int err; 49 | cl_event event; 50 | 51 | // get corresponding cl_kernel 52 | cl_kernel kernel = clCreateKernel( 53 | program, "arrayTest", &err); 54 | 55 | if (!kernel || err != CL_SUCCESS) { 56 | throw std::runtime_error( 57 | "Failed to create compute kernel arrayTest"); 58 | } 59 | 60 | // get the pointer to input/output data 61 | cl_mem ocl_data = *((cl_mem*)getInput(0)); 62 | cl_mem ocl_weights = *((cl_mem*)getInput(1)); 63 | cl_mem ocl_output = *((cl_mem*)getOutput( 64 | 0, item_length, num_samples, 65 | sizeof(double))); 66 | 67 | if (!ocl_data || !ocl_weights || !ocl_output) { 68 | throw std::runtime_error("Buffer are not allocated"); 69 | } 70 | 71 | // Set the arguments to our compute kernel 72 | err = clSetKernelArg(kernel, 0, sizeof(int), &weight_length); 73 | err |= clSetKernelArg(kernel, 1, sizeof(int), &num_samples); 74 | err |= clSetKernelArg(kernel, 2, sizeof(int), &item_length); 75 | err |= clSetKernelArg(kernel, 3, sizeof(cl_mem), &ocl_weights); 76 | err |= clSetKernelArg(kernel, 4, sizeof(cl_mem), &ocl_data); 77 | err |= clSetKernelArg(kernel, 5, sizeof(cl_mem), &ocl_output); 78 | if (err != CL_SUCCESS) { 79 | throw std::runtime_error("Cannot set kernel args\n"); 80 | } 81 | 82 | size_t work_lsize[1] = {128}; 83 | size_t work_gsize[1]; 84 | work_gsize[0] = 64*work_lsize[0]; 85 | 86 | err = clEnqueueNDRangeKernel(command, kernel, 1, NULL, work_gsize, work_lsize, 0, NULL, &event); 87 | clWaitForEvents(1, &event); 88 | } 89 | catch (std::runtime_error &e) { 90 | throw e; 91 | } 92 | } 93 | }; 94 | 95 | extern "C" Task* create() { 96 | return new ArrayTest(); 97 | } 98 | 99 | extern "C" void destroy(Task* p) { 100 | delete p; 101 | } 102 | -------------------------------------------------------------------------------- /functional-test/arraytest/ocl_task/Makefile: -------------------------------------------------------------------------------- 1 | ifeq ($(BLAZE_HOME),) 2 | $(error BLAZE_HOME not set) 3 | endif 4 | ifeq ("$(wildcard $(BLAZE_HOME)/Makefile.config)","") 5 | $(error BLAZE_HOME not set properly in environment) 6 | endif 7 | 8 | MANAGER_DIR=$(BLAZE_HOME)/manager 9 | PLATFORM_DIR=$(BLAZE_HOME)/platforms/gpu-ocl 10 | include $(BLAZE_HOME)/Makefile.config 11 | 12 | PP=g++ 13 | CC=gcc 14 | 15 | CFLAGS= -shared -fPIC -std=c++0x -m64 -g 16 | COMPILE= $(CFLAGS) \ 17 | -I$(MANAGER_DIR)/include \ 18 | -I$(MANAGER_DIR)/src \ 19 | -I$(PLATFORM_DIR) \ 20 | -I$(BOOST_DIR)/include \ 21 | -I$(PROTOBUF_DIR)/include \ 22 | -I$(HADOOP_DIR)/include \ 23 | -I$(CUDA_DIR)/include 24 | 25 | ACC = ArrayTest 26 | 27 | OBJS= $(addsuffix .so, $(ACC)) 28 | 29 | all: $(OBJS) 30 | 31 | %.so: %.cpp Makefile 32 | $(PP) $(COMPILE) $< -o $@ 33 | 34 | clean: 35 | rm -rf $(OBJS) 36 | -------------------------------------------------------------------------------- /functional-test/conf.prototxt: -------------------------------------------------------------------------------- 1 | port : 1027 2 | verbose : 2 3 | platform : { 4 | cache_limit: 16384 5 | scratch_limit: 4096 6 | acc : { 7 | id : "Tuple2Test" 8 | path : "functional-test/tuple2test/Tuple2Test.so" 9 | } 10 | acc : { 11 | id : "MaskTest" 12 | path : "functional-test/masktest/MaskTest.so" 13 | } 14 | acc : { 15 | id : "MapTest" 16 | path : "functional-test/maptest/MapTest.so" 17 | } 18 | acc : { 19 | id : "ArrayTest" 20 | path : "functional-test/arraytest/ArrayTest.so" 21 | } 22 | } 23 | -------------------------------------------------------------------------------- /functional-test/masktest/acc_task/Makefile: -------------------------------------------------------------------------------- 1 | MANAGER_DIR=../../../manager 2 | include ../../../Makefile.config 3 | 4 | # check all variables 5 | ifeq ($(BOOST_DIR),) 6 | $(error BOOST_DIR not set properly in Makefile.config) 7 | endif 8 | ifeq ($(PROTOBUF_DIR),) 9 | $(error PROTOBUF_DIR not set properly in Makefile.config) 10 | endif 11 | PP=g++ 12 | CC=gcc 13 | 14 | CFLAGS= -shared -fPIC -std=c++0x -m64 -g 15 | COMPILE= $(CFLAGS) \ 16 | -I$(MANAGER_DIR)/include \ 17 | -I$(BOOST_DIR)/include \ 18 | -I$(PROTOBUF_DIR)/include 19 | 20 | ACC = MaskTest 21 | 22 | OBJS= $(addsuffix .so, $(addprefix ../, $(ACC))) 23 | 24 | all: $(OBJS) 25 | 26 | ../%.so: %.cpp Makefile 27 | $(PP) $(COMPILE) $< -o $@ 28 | 29 | clean: 30 | rm -rf $(OBJS) 31 | -------------------------------------------------------------------------------- /functional-test/masktest/acc_task/MaskTest.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | #include "blaze.h" 5 | 6 | using namespace blaze; 7 | 8 | class MaskTest : public Task { 9 | public: 10 | 11 | // extends the base class constructor 12 | // to indicate how many input blocks 13 | // are required 14 | MaskTest(): Task(1) {;} 15 | 16 | // overwrites the compute function 17 | virtual void compute() { 18 | 19 | // get input data length 20 | int data_length = getInputLength(0); 21 | 22 | // get the pointer to input/output data 23 | double* a = (double*)getInput(0); 24 | double* b = (double*)getOutput(0, 1, data_length, sizeof(double)); 25 | 26 | // perform computation 27 | for (int i=0; i 2 | 16 | 17 | test 18 | test 19 | jar 20 | "MaskTest" 21 | 4.0.0 22 | 0.0.0 23 | 24 | 25 | 26 | scala-tools.org 27 | Scala-tools Maven2 Repository 28 | http://scala-tools.org/repo-releases 29 | 30 | 31 | maven-hadoop 32 | Hadoop Releases 33 | https://repository.cloudera.com/content/repositories/releases/ 34 | 35 | 36 | cloudera-repos 37 | Cloudera Repos 38 | https://repository.cloudera.com/artifactory/cloudera-repos/ 39 | 40 | 41 | 42 | 43 | 44 | scala-tools.org 45 | Scala-tools Maven2 Repository 46 | http://scala-tools.org/repo-releases 47 | 48 | 49 | 50 | 51 | UTF-8 52 | UTF-8 53 | 54 | 55 | 56 | 57 | 58 | org.scala-tools 59 | maven-scala-plugin 60 | 2.15.2 61 | 62 | 63 | 64 | compile 65 | 66 | 67 | 68 | 69 | 70 | maven-compiler-plugin 71 | 3.1 72 | 73 | 1.6 74 | 1.6 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | org.scala-lang 83 | scala-library 84 | 2.11.4 85 | 86 | 87 | org.apache.spark 88 | spark-core_2.10 89 | 1.3.1 90 | 91 | 92 | org.apache.spark 93 | blaze 94 | 1.0-SNAPSHOT 95 | 96 | 97 | 98 | -------------------------------------------------------------------------------- /functional-test/masktest/app/src/main/scala/testapp/MaskTest.scala: -------------------------------------------------------------------------------- 1 | /* 2 | * Licensed to the Apache Software Foundation (ASF) under one or more 3 | * contributor license agreements. See the NOTICE file distributed with 4 | * this work for additional information regarding copyright ownership. 5 | * The ASF licenses this file to You under the Apache License, Version 2.0 6 | * (the "License"); you may not use this file except in compliance with 7 | * the License. You may obtain a copy of the License at 8 | * 9 | * http://www.apache.org/licenses/LICENSE-2.0 10 | * 11 | * Unless required by applicable law or agreed to in writing, software 12 | * distributed under the License is distributed on an "AS IS" BASIS, 13 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 | * See the License for the specific language governing permissions and 15 | * limitations under the License. 16 | */ 17 | 18 | import org.apache.spark.SparkContext 19 | import org.apache.spark.SparkContext._ 20 | import org.apache.spark.SparkConf 21 | import org.apache.spark.util.random._ 22 | import Array._ 23 | import scala.util.Random 24 | import org.apache.spark.rdd._ 25 | import java.net._ 26 | 27 | // comaniac: Import extended package 28 | import org.apache.spark.blaze._ 29 | 30 | class MaskTest() extends Accelerator[Double, Double] { 31 | val id: String = "MaskTest" 32 | 33 | def getArg(idx: Int): Option[_] = None 34 | def getArgNum(): Int = 0 35 | 36 | override def call(in: Iterator[Double]): Iterator[Double] = { 37 | in.filter { a => 38 | a > 0.5 39 | } 40 | } 41 | } 42 | 43 | object TestApp { 44 | def main(args : Array[String]) { 45 | val sc = get_spark_context("Test App") 46 | println("Functional test: AccRDD.sample_acc") 47 | println("Set random seed as 904401792 to activate TestSampler.") 48 | 49 | val rander = new Random(0) 50 | val data = new Array[Double](150).map(e => rander.nextDouble) 51 | val rdd = sc.parallelize(data, 4).cache() 52 | 53 | val acc = new BlazeRuntime(sc) 54 | val rdd_acc = acc.wrap(rdd) 55 | 56 | val rdd_sampled = rdd_acc.sample_acc(true, 0.4, 904401792) 57 | val res_acc = rdd_sampled.mapPartitions_acc(new MaskTest()).collect 58 | val res_cpu = rdd.mapPartitions(iter => { 59 | val out = new Array[Double](30) 60 | for (i <- 0 until 30) 61 | out(i) = iter.next 62 | out.iterator 63 | }).collect 64 | 65 | if (res_cpu.deep != res_acc.deep) { 66 | println("CPU result: \n" + res_cpu.deep.mkString("\n")) 67 | println("ACC result: \n" + res_acc.deep.mkString("\n")) 68 | } else { 69 | println("result correct") 70 | } 71 | 72 | acc.stop() 73 | } 74 | 75 | def get_spark_context(appName : String) : SparkContext = { 76 | val conf = new SparkConf() 77 | conf.setAppName(appName) 78 | 79 | return new SparkContext(conf) 80 | } 81 | } 82 | 83 | -------------------------------------------------------------------------------- /functional-test/tuple2test/acc_task/Makefile: -------------------------------------------------------------------------------- 1 | ifeq ($(BLAZE_HOME),) 2 | $(error BLAZE_HOME not set) 3 | endif 4 | ifeq ("$(wildcard $(BLAZE_HOME)/Makefile.config)","") 5 | $(error BLAZE_HOME not set properly in environment) 6 | endif 7 | 8 | MANAGER_DIR=$(BLAZE_HOME)/manager 9 | include $(BLAZE_HOME)/Makefile.config 10 | 11 | # check all variables 12 | ifeq ($(BOOST_DIR),) 13 | $(error BOOST_DIR not set properly in Makefile.config) 14 | endif 15 | ifeq ($(PROTOBUF_DIR),) 16 | $(error PROTOBUF_DIR not set properly in Makefile.config) 17 | endif 18 | PP=g++ 19 | CC=gcc 20 | 21 | CFLAGS= -shared -fPIC -std=c++0x -m64 -g 22 | COMPILE= $(CFLAGS) \ 23 | -I$(MANAGER_DIR)/include \ 24 | -I$(BOOST_DIR)/include \ 25 | -I$(PROTOBUF_DIR)/include 26 | 27 | ACC = Tuple2Test 28 | 29 | OBJS= $(addsuffix .so, $(addprefix ../, $(ACC))) 30 | 31 | all: $(OBJS) 32 | 33 | ../%.so: %.cpp Makefile 34 | $(PP) $(COMPILE) $< -o $@ 35 | 36 | clean: 37 | rm -rf $(OBJS) 38 | -------------------------------------------------------------------------------- /functional-test/tuple2test/acc_task/Tuple2Test.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | #include "blaze.h" 5 | 6 | using namespace blaze; 7 | 8 | class Tuple2Test : public Task { 9 | public: 10 | 11 | // extends the base class constructor 12 | // to indicate how many input blocks 13 | // are required 14 | Tuple2Test(): Task(2) {;} 15 | 16 | // overwrites the compute function 17 | virtual void compute() { 18 | 19 | // get input data length 20 | int data_length = getInputLength(0); 21 | 22 | // get the pointer to input/output data 23 | int* a = (int*)getInput(0); 24 | int* b = (int*)getInput(1); 25 | int* c = (int*)getOutput(0, 1, data_length, sizeof(int)); 26 | 27 | // perform computation 28 | for (int i=0; i 2 | 16 | 17 | test 18 | test 19 | jar 20 | "Tuple2Test" 21 | 4.0.0 22 | 0.0.0 23 | 24 | 25 | 26 | scala-tools.org 27 | Scala-tools Maven2 Repository 28 | http://scala-tools.org/repo-releases 29 | 30 | 31 | maven-hadoop 32 | Hadoop Releases 33 | https://repository.cloudera.com/content/repositories/releases/ 34 | 35 | 36 | cloudera-repos 37 | Cloudera Repos 38 | https://repository.cloudera.com/artifactory/cloudera-repos/ 39 | 40 | 41 | 42 | 43 | 44 | scala-tools.org 45 | Scala-tools Maven2 Repository 46 | http://scala-tools.org/repo-releases 47 | 48 | 49 | 50 | 51 | UTF-8 52 | UTF-8 53 | 54 | 55 | 56 | 57 | 58 | org.scala-tools 59 | maven-scala-plugin 60 | 2.15.2 61 | 62 | 63 | 64 | compile 65 | 66 | 67 | 68 | 69 | 70 | maven-compiler-plugin 71 | 3.1 72 | 73 | 1.6 74 | 1.6 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | org.scala-lang 83 | scala-library 84 | 2.11.4 85 | 86 | 87 | org.apache.spark 88 | spark-core_2.10 89 | 1.3.1 90 | 91 | 92 | org.apache.spark 93 | blaze 94 | 1.0-SNAPSHOT 95 | 96 | 97 | 98 | -------------------------------------------------------------------------------- /functional-test/tuple2test/app/src/main/scala/testapp/Tuple2Test.scala: -------------------------------------------------------------------------------- 1 | /* 2 | * Licensed to the Apache Software Foundation (ASF) under one or more 3 | * contributor license agreements. See the NOTICE file distributed with 4 | * this work for additional information regarding copyright ownership. 5 | * The ASF licenses this file to You under the Apache License, Version 2.0 6 | * (the "License"); you may not use this file except in compliance with 7 | * the License. You may obtain a copy of the License at 8 | * 9 | * http://www.apache.org/licenses/LICENSE-2.0 10 | * 11 | * Unless required by applicable law or agreed to in writing, software 12 | * distributed under the License is distributed on an "AS IS" BASIS, 13 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 | * See the License for the specific language governing permissions and 15 | * limitations under the License. 16 | */ 17 | 18 | import org.apache.spark.SparkContext 19 | import org.apache.spark.SparkContext._ 20 | import org.apache.spark.SparkConf 21 | import org.apache.spark.util.random._ 22 | import Array._ 23 | import scala.math._ 24 | import org.apache.spark.rdd._ 25 | import java.net._ 26 | 27 | // comaniac: Import extended package 28 | import org.apache.spark.blaze._ 29 | 30 | // TODO: Tuple2 as an output type 31 | class Tuple2Test extends Accelerator[Tuple2[Double, Double], Double] { 32 | val id: String = "Tuple2Test" 33 | 34 | def getArgNum(): Int = 0 35 | 36 | def getArg(idx: Int): Option[_] = None 37 | 38 | override def call(in: Tuple2[Double, Double]): Double = { 39 | in._1 + in._2 40 | } 41 | 42 | override def call(in: Iterator[Tuple2[Double, Double]]): Iterator[Double] = { 43 | val inAry = in.toArray 44 | val length: Int = inAry.length 45 | val outAry = new Array[Double](length) 46 | 47 | for (i <- 0 until length) 48 | outAry(i) = inAry(i)._1 + inAry(i)._2 49 | 50 | outAry.iterator 51 | } 52 | } 53 | 54 | object TestApp { 55 | def main(args : Array[String]) { 56 | val sc = get_spark_context("Tuple2 Test") 57 | val data = new Array[Double](1024).map(e => (random, random)) 58 | val rdd = sc.parallelize(data, 8).cache 59 | 60 | val acc = new BlazeRuntime(sc) 61 | val rdd_acc = acc.wrap(rdd) 62 | 63 | println("map Result: " + rdd_acc.map_acc(new Tuple2Test).reduce((a, b) => (a + b))) 64 | println("mapPartition Result: " + rdd_acc.mapPartitions_acc(new Tuple2Test).reduce((a, b) => (a + b))) 65 | println("CPU Result: " + rdd_acc.map({case (a, b) => (a + b)}).reduce((a, b) => (a + b))) 66 | 67 | acc.stop() 68 | } 69 | 70 | def get_spark_context(appName : String) : SparkContext = { 71 | val conf = new SparkConf() 72 | conf.setAppName(appName) 73 | 74 | return new SparkContext(conf) 75 | } 76 | } 77 | 78 | -------------------------------------------------------------------------------- /manager/bin/.gitignore: -------------------------------------------------------------------------------- 1 | # Ignore everything in this directory 2 | * 3 | # Except this file 4 | !.gitignore 5 | -------------------------------------------------------------------------------- /manager/include/blaze/AccAgent.h: -------------------------------------------------------------------------------- 1 | #ifndef ACCAGENT_H 2 | #define ACCAGENT_H 3 | 4 | #include 5 | 6 | #include "Common.h" 7 | #include "Task.h" 8 | #include "proto/acc_conf.pb.h" 9 | 10 | namespace blaze { 11 | 12 | typedef boost::shared_ptr ManagerConf_ptr; 13 | 14 | class AccAgent { 15 | public: 16 | AccAgent(const char* conf_path); 17 | 18 | Task_ptr createTask(std::string acc_id); 19 | 20 | void writeInput(Task_ptr task, 21 | std::string acc_id, 22 | void* data_ptr, 23 | int num_items, 24 | int item_length, 25 | int data_width); 26 | 27 | void readOutput(Task_ptr task, 28 | void* data_ptr, 29 | size_t data_size); 30 | 31 | private: 32 | ManagerConf_ptr conf_; 33 | PlatformManager_ptr platform_manager_; 34 | }; 35 | 36 | } // namespace blaze 37 | #endif 38 | -------------------------------------------------------------------------------- /manager/include/blaze/Admin.h: -------------------------------------------------------------------------------- 1 | #ifndef ADMIN_H 2 | #define ADMIN_H 3 | 4 | #include "proto/task.pb.h" 5 | #include "proto/acc_conf.pb.h" 6 | 7 | #include "Common.h" 8 | 9 | // for testing purpose 10 | #ifndef TEST_FRIENDS_LIST 11 | #define TEST_FRIENDS_LIST 12 | #endif 13 | 14 | namespace blaze { 15 | 16 | class Admin { 17 | TEST_FRIENDS_LIST 18 | public: 19 | Admin(std::string _ip = "127.0.0.1"); 20 | 21 | bool registerAcc(ManagerConf &conf); 22 | bool deleteAcc(ManagerConf &conf); 23 | 24 | private: 25 | 26 | void sendMessage(TaskMsg &msg); 27 | 28 | // data structures for socket connection 29 | int nam_port; 30 | std::string ip_address; 31 | ios_ptr ios; 32 | endpoint_ptr endpoint; 33 | }; 34 | 35 | } // namespace blaze 36 | #endif 37 | -------------------------------------------------------------------------------- /manager/include/blaze/Block.h: -------------------------------------------------------------------------------- 1 | #ifndef BLOCK_H 2 | #define BLOCK_H 3 | 4 | #include 5 | 6 | #include "Common.h" 7 | 8 | /* 9 | * base class extendable to manage memory block 10 | * on other memory space (e.g. FPGA device memory) 11 | */ 12 | 13 | namespace blaze { 14 | 15 | class DataBlock 16 | : public boost::basic_lockable_adapter 17 | { 18 | 19 | public: 20 | 21 | // create basic data block 22 | DataBlock(int _num_items, 23 | int _item_length, 24 | int _item_size, 25 | int _align_width = 0, 26 | int _flag = BLAZE_INPUT_BLOCK); 27 | 28 | DataBlock(const DataBlock &block); 29 | 30 | ~DataBlock(); 31 | 32 | // allocate data aligned to a given width 33 | void alloc(int _align_width); 34 | 35 | // allocate data 36 | virtual void alloc(); 37 | 38 | // copy data from an array 39 | virtual void writeData(void* src, size_t _size); 40 | 41 | // copy data from an array with offset 42 | virtual void writeData(void* src, size_t _size, size_t offset); 43 | 44 | // write data to an array 45 | virtual void readData(void* dst, size_t size); 46 | 47 | // get the pointer to data 48 | virtual char* getData(); 49 | 50 | // sample the items in the block by a mask 51 | virtual boost::shared_ptr sample(char* mask); 52 | 53 | virtual void readFromMem(std::string path); 54 | virtual void writeToMem(std::string path); 55 | 56 | int getNumItems() { return num_items; } 57 | int getItemLength() { return item_length; } 58 | int getItemSize() { return item_size; } 59 | int getLength() { return length; } 60 | int getSize() { return size; } 61 | int getFlag() { return flag; } 62 | 63 | // status check of DataBlock needs to be exclusive 64 | bool isAllocated(); 65 | bool isReady(); 66 | 67 | protected: 68 | int flag; /* enum: input, shared, output */ 69 | int item_length; /* number of elements per data item */ 70 | int item_size; /* byte size per data item */ 71 | int num_items; /* number of data items per data block */ 72 | int data_width; /* byte size per element */ 73 | int align_width; /* align data width per data item */ 74 | int length; /* total number of elements */ 75 | int64_t size; /* total byte size of the data block */ 76 | 77 | bool allocated; 78 | bool aligned; 79 | bool ready; 80 | bool copied; 81 | 82 | private: 83 | char* data; 84 | }; 85 | 86 | const DataBlock_ptr NULL_DATA_BLOCK; 87 | 88 | } 89 | #endif 90 | -------------------------------------------------------------------------------- /manager/include/blaze/BlockManager.h: -------------------------------------------------------------------------------- 1 | #ifndef BLOCK_MANAGER_H 2 | #define BLOCK_MANAGER_H 3 | 4 | #include 5 | #include 6 | #include 7 | #include 8 | #include 9 | 10 | #include 11 | #include 12 | #include 13 | #include 14 | 15 | #include "Common.h" 16 | 17 | namespace blaze { 18 | 19 | /** 20 | * BlockManager holds two spaces of memory 21 | * - scratch: for shared data across many tasks of the same stage, 22 | * will be explicitly deleted after the stage finishes. 23 | * Aligned with Spark broadcast 24 | * - cache: hold all input blocks, and is managed on a LRU basis 25 | */ 26 | 27 | class BlockManager 28 | : public boost::basic_lockable_adapter 29 | { 30 | public: 31 | 32 | BlockManager( 33 | Platform* _platform, 34 | size_t _maxCacheSize = (1L<<30), 35 | size_t _maxScratchSize = (1L<<28) 36 | ): 37 | cacheSize(0), scratchSize(0), 38 | maxCacheSize(_maxCacheSize), 39 | maxScratchSize(_maxScratchSize), 40 | platform(_platform) 41 | {;} 42 | 43 | // check scratch and cache table to see if a certain block exists 44 | virtual bool contains(int64_t tag) { 45 | if (tag < 0) { 46 | // check scratch table 47 | return (scratchTable.find(tag) != scratchTable.end()); 48 | } 49 | else { 50 | // check cache table 51 | return (cacheTable.find(tag) != cacheTable.end()); 52 | } 53 | } 54 | 55 | // create a block and add it to cache/scratch 56 | // return true if a new block is created 57 | virtual bool getAlloc(int64_t tag, DataBlock_ptr &block, 58 | int num_items, int item_length, int item_size, int align_width=0); 59 | 60 | // get a block from cache table or scratch table 61 | virtual DataBlock_ptr get(int64_t tag); 62 | 63 | // remove a block from scratch table 64 | virtual void remove(int64_t tag); 65 | 66 | private: 67 | // internal cache operations 68 | void do_add(int64_t tag, DataBlock_ptr block); 69 | void evict(); 70 | void update(int64_t tag); 71 | 72 | // index (tag) to scratch table 73 | std::map scratchTable; 74 | 75 | // index (tag) to cached block and its access count 76 | std::map > cacheTable; 77 | 78 | size_t maxCacheSize; 79 | size_t maxScratchSize; 80 | size_t cacheSize; 81 | size_t scratchSize; 82 | 83 | Platform* platform; 84 | }; 85 | 86 | } 87 | 88 | #endif 89 | -------------------------------------------------------------------------------- /manager/include/blaze/Client.h: -------------------------------------------------------------------------------- 1 | #ifndef CLIENT_H 2 | #define CLIENT_H 3 | 4 | #include "proto/task.pb.h" 5 | #include "Common.h" 6 | 7 | #define BLAZE_INPUT 0 8 | #define BLAZE_INPUT_CACHED 1 9 | #define BLAZE_SHARED 2 10 | 11 | // for testing purpose 12 | #ifndef TEST_FRIENDS_LIST 13 | #define TEST_FRIENDS_LIST 14 | #endif 15 | 16 | using namespace boost::asio; 17 | 18 | namespace blaze { 19 | 20 | typedef boost::shared_ptr client_event; 21 | 22 | class Client { 23 | TEST_FRIENDS_LIST 24 | public: 25 | Client(std::string _acc_id, 26 | int _num_inputs, 27 | int _num_outputs, 28 | int port = 1027); 29 | 30 | void* createInput( int idx, 31 | int num_items, 32 | int item_length, 33 | int data_width, 34 | int type = BLAZE_INPUT); 35 | 36 | void* createOutput(int idx, 37 | int num_items, 38 | int item_length, 39 | int data_width); 40 | 41 | // copy data to an input block from a pointer, 42 | // allocate the space if the block has not been created 43 | void setInput(int idx, void* src, 44 | int num_items = 0, 45 | int item_length = 0, 46 | int data_width = 0, 47 | int type = BLAZE_INPUT); 48 | 49 | // get the data pointer and information of an input block 50 | void* getInputPtr(int idx); 51 | int getInputNumItems(int idx); 52 | int getInputLength(int idx); 53 | 54 | // get the data pointer and information of an output block 55 | void* getOutputPtr(int idx); 56 | int getOutputNumItems(int idx); 57 | int getOutputLength(int idx); 58 | 59 | // start client and wait for results 60 | // NOTE: in current version the call is blocking no matter 61 | // what input is provided 62 | void start(bool blocking = true); 63 | 64 | // pure virtual method to be overloaded 65 | virtual void compute() = 0; 66 | 67 | private: 68 | // helper functions in communication flow 69 | void prepareRequest(TaskMsg &msg); 70 | void prepareData(TaskMsg &data_msg, TaskMsg &reply_msg); 71 | void processOutput(TaskMsg &msg); 72 | 73 | // routine function for socket communication 74 | //void recv(TaskMsg&, socket_ptr); 75 | //void send(TaskMsg&, socket_ptr); 76 | 77 | std::string acc_id; 78 | std::string app_id; 79 | 80 | // data structures for socket connection 81 | int srv_port; 82 | std::string ip_address; 83 | ios_ptr ios; 84 | endpoint_ptr endpoint; 85 | 86 | // input/output data blocks 87 | int num_inputs; 88 | int num_outputs; 89 | std::vector input_blocks; 90 | std::vector output_blocks; 91 | std::vector > block_info; 92 | }; 93 | 94 | } // namespace blaze 95 | 96 | #endif 97 | -------------------------------------------------------------------------------- /manager/include/blaze/CommManager.h: -------------------------------------------------------------------------------- 1 | #ifndef COMM_H 2 | #define COMM_H 3 | 4 | #include 5 | 6 | #include "proto/task.pb.h" 7 | #include "Common.h" 8 | 9 | // for testing purpose 10 | #ifndef TEST_FRIENDS_LIST 11 | #define TEST_FRIENDS_LIST 12 | #endif 13 | 14 | using namespace boost::asio; 15 | 16 | namespace blaze { 17 | 18 | /* 19 | * Communicator design for Node Manager 20 | */ 21 | class CommManager 22 | : public boost::basic_lockable_adapter 23 | { 24 | TEST_FRIENDS_LIST 25 | public: 26 | CommManager( 27 | PlatformManager* _platform, 28 | std::string address = "127.0.0.1", 29 | int ip_port = 1027, 30 | int _max_threads = boost::thread::hardware_concurrency()); 31 | 32 | ~CommManager(); 33 | 34 | protected: 35 | // pure virtual method called by listen 36 | virtual void process(socket_ptr) = 0; 37 | 38 | // reference to platform manager 39 | PlatformManager *platform_manager; 40 | 41 | private: 42 | void startAccept(); 43 | void handleAccept( 44 | const boost::system::error_code& error, 45 | socket_ptr socket); 46 | 47 | int srv_port; 48 | std::string ip_address; 49 | 50 | ios_ptr ios; 51 | endpoint_ptr endpoint; 52 | acceptor_ptr acceptor; 53 | boost::thread_group comm_threads; 54 | }; 55 | 56 | // Manage communication with Application 57 | class AppCommManager : public CommManager 58 | { 59 | TEST_FRIENDS_LIST 60 | public: 61 | AppCommManager( 62 | PlatformManager* _platform, 63 | std::string address = "127.0.0.1", 64 | int ip_port = 1027 65 | ): CommManager(_platform, address, ip_port, 24) {;} 66 | private: 67 | void process(socket_ptr); 68 | void handleAccRegister(TaskMsg &msg); 69 | void handleAccDelete(TaskMsg &msg); 70 | }; 71 | 72 | class AccReject : public std::logic_error { 73 | public: 74 | explicit AccReject(const std::string& what_arg): 75 | std::logic_error(what_arg) {;} 76 | }; 77 | 78 | class AccFailure : public std::logic_error { 79 | public: 80 | explicit AccFailure(const std::string& what_arg): 81 | std::logic_error(what_arg) {;} 82 | }; 83 | 84 | // Manager communication with GAM 85 | class GAMCommManager : public CommManager 86 | { 87 | TEST_FRIENDS_LIST 88 | public: 89 | GAMCommManager( 90 | PlatformManager* _platform, 91 | std::string address = "127.0.0.1", 92 | int ip_port = 1028 93 | ): CommManager(_platform, address, ip_port, 4) {;} 94 | private: 95 | void process(socket_ptr); 96 | std::vector > last_labels; 97 | }; 98 | } // namespace blaze 99 | #endif 100 | -------------------------------------------------------------------------------- /manager/include/blaze/Common.h: -------------------------------------------------------------------------------- 1 | #ifndef COMMON_H 2 | #define COMMON_H 3 | 4 | #include 5 | #include 6 | #include 7 | #include 8 | #include 9 | #include 10 | #include 11 | #include 12 | #include 13 | #include 14 | #include 15 | #include 16 | #include 17 | #include 18 | #include 19 | 20 | namespace blaze { 21 | 22 | // constant parameter definition 23 | #define BLAZE_INPUT_BLOCK 0 24 | #define BLAZE_SHARED_BLOCK 1 25 | #define BLAZE_OUTPUT_BLOCK 2 26 | 27 | // forward declaration of all classes 28 | class BlockManager; 29 | class CommManager; 30 | class DataBlock; 31 | class Task; 32 | class TaskEnv; 33 | class TaskManager; 34 | class Platform; 35 | class PlatformManager; 36 | class QueueManager; 37 | 38 | // typedef of boost smart pointer object 39 | typedef boost::shared_ptr BlockManager_ptr; 40 | typedef boost::shared_ptr CommManager_ptr; 41 | typedef boost::shared_ptr DataBlock_ptr; 42 | typedef boost::weak_ptr DataBlock_ref; 43 | typedef boost::shared_ptr Platform_ptr; 44 | typedef boost::weak_ptr Platform_ref; 45 | typedef boost::shared_ptr PlatformManager_ptr; 46 | typedef boost::shared_ptr QueueManager_ptr; 47 | typedef boost::shared_ptr Task_ptr; 48 | typedef boost::shared_ptr TaskEnv_ptr; 49 | typedef boost::shared_ptr TaskManager_ptr; 50 | typedef boost::weak_ptr TaskManager_ref; 51 | 52 | typedef boost::shared_ptr ios_ptr; 53 | typedef boost::shared_ptr endpoint_ptr; 54 | typedef boost::shared_ptr socket_ptr; 55 | typedef boost::shared_ptr acceptor_ptr; 56 | 57 | // helper functions to get system info 58 | uint64_t getUs(); 59 | uint64_t getMs(); 60 | uint32_t getTid(); 61 | std::string getTS(); 62 | std::string getUid(); 63 | std::string getHostname(); 64 | 65 | // helper functions for socket transfer 66 | void recv(::google::protobuf::Message&, socket_ptr); 67 | void send(::google::protobuf::Message&, socket_ptr); 68 | 69 | // helper functions for file/directory operations 70 | std::string saveFile(std::string path, const std::string &contents); 71 | std::string readFile(std::string path); 72 | bool deleteFile(std::string path); 73 | 74 | // parameters 75 | static std::string local_dir("/tmp"); 76 | 77 | // custom exceptions 78 | class invalidParam : public std::runtime_error { 79 | public: 80 | explicit invalidParam(const std::string& what_arg): 81 | std::runtime_error(what_arg) {;} 82 | }; 83 | 84 | class commError : public std::runtime_error { 85 | public: 86 | explicit commError(const std::string& what_arg): 87 | std::runtime_error(what_arg) {;} 88 | }; 89 | 90 | class fileError : public std::runtime_error { 91 | public: 92 | explicit fileError(const std::string& what_arg): 93 | std::runtime_error(what_arg) {;} 94 | }; 95 | 96 | class internalError : public std::runtime_error { 97 | public: 98 | explicit internalError(const std::string& what_arg): 99 | std::runtime_error(what_arg) {;} 100 | }; 101 | } // namespace blaze 102 | 103 | #endif 104 | -------------------------------------------------------------------------------- /manager/include/blaze/Platform.h: -------------------------------------------------------------------------------- 1 | #ifndef PLATFORM_H 2 | #define PLATFORM_H 3 | 4 | #include "proto/acc_conf.pb.h" 5 | #include "Common.h" 6 | 7 | namespace blaze { 8 | 9 | class Platform { 10 | friend class PlatformManager; 11 | 12 | public: 13 | Platform(std::map &conf_table); 14 | 15 | virtual void addQueue(AccWorker &conf); 16 | virtual void removeQueue(std::string id); 17 | 18 | // store an accelerator setup on the platform 19 | //virtual void setupAcc(AccWorker &conf); 20 | 21 | // obtain a BlockManager 22 | virtual void createBlockManager(size_t cache_limit, size_t scratch_limit); 23 | 24 | virtual BlockManager* getBlockManager(); 25 | 26 | virtual TaskManager_ref getTaskManager(std::string id); 27 | 28 | virtual QueueManager* getQueueManager(); 29 | 30 | // create a block object for the specific platform 31 | virtual DataBlock_ptr createBlock( 32 | int num_items, 33 | int item_length, 34 | int item_size, 35 | int align_width = 0, 36 | int flag = BLAZE_INPUT_BLOCK); 37 | 38 | virtual DataBlock_ptr createBlock(const DataBlock&); 39 | 40 | virtual void remove(int64_t block_id); 41 | 42 | // get an entry in the config_table matching the key 43 | std::string getConfig(std::string &key); 44 | 45 | // get TaskEnv to pass to Task 46 | virtual TaskEnv_ptr getEnv(std::string id); 47 | 48 | protected: 49 | BlockManager_ptr block_manager; 50 | QueueManager_ptr queue_manager; 51 | 52 | // a table storing platform configurations mapped by key 53 | std::map config_table; 54 | 55 | // a table storing platform configurations mapped by key 56 | std::map acc_table; 57 | 58 | private: 59 | TaskEnv_ptr env; 60 | }; 61 | 62 | } // namespace blaze 63 | #endif 64 | -------------------------------------------------------------------------------- /manager/include/blaze/PlatformManager.h: -------------------------------------------------------------------------------- 1 | #ifndef PLATFORM_MANAGER_H 2 | #define PLATFORM_MANAGER_H 3 | 4 | #include 5 | #include 6 | #include 7 | 8 | #include 9 | 10 | #include "proto/acc_conf.pb.h" 11 | #include "Common.h" 12 | 13 | namespace blaze { 14 | 15 | class PlatformManager 16 | : public boost::basic_lockable_adapter 17 | { 18 | 19 | friend class AppCommManager; 20 | 21 | public: 22 | 23 | PlatformManager(ManagerConf *conf); 24 | 25 | bool accExists(std::string acc_id); 26 | bool platformExists(std::string platform); 27 | 28 | Platform* getPlatformByAccId(std::string acc_id); 29 | 30 | Platform* getPlatformById(std::string platform_id); 31 | 32 | TaskManager_ref getTaskManager(std::string acc_id); 33 | 34 | // remove a shared block from all platforms 35 | void removeShared(int64_t block_id); 36 | 37 | std::vector > getLabels(); 38 | 39 | private: 40 | // create a new platform from file 41 | Platform_ptr create( 42 | std::string id, 43 | std::map &conf_table); 44 | 45 | void registerAcc( 46 | std::string platform_id, 47 | AccWorker &acc_conf); 48 | 49 | void removeAcc( 50 | std::string requester, 51 | std::string acc_id, 52 | std::string platform_id); 53 | 54 | // map platform_id to Platform 55 | std::map platform_table; 56 | 57 | // map acc_id to accelerator platform 58 | std::map acc_table; 59 | 60 | // map acc_id to BlockManager platform 61 | // TODO: should be deprecated 62 | std::map cache_table; 63 | }; 64 | } // namespace blaze 65 | #endif 66 | -------------------------------------------------------------------------------- /manager/include/blaze/QueueManager.h: -------------------------------------------------------------------------------- 1 | #ifndef QUEUE_MANAGER_H 2 | #define QUEUE_MANAGER_H 3 | 4 | #include "proto/acc_conf.pb.h" 5 | #include "Common.h" 6 | 7 | namespace blaze { 8 | 9 | class QueueManager 10 | : public boost::basic_lockable_adapter 11 | { 12 | 13 | public: 14 | QueueManager(Platform *_platform): 15 | platform(_platform) 16 | {;} 17 | 18 | // add a new queue regarding an existing accelerator 19 | void add(std::string id, std::string lib_path); 20 | 21 | // remove a task manager in queue_table 22 | void remove(std::string id); 23 | 24 | // start the executor for one task queue 25 | virtual void start(std::string id); 26 | 27 | // request the task manager by acc id 28 | TaskManager_ptr get(std::string id); 29 | 30 | // read TaskEnv for scheduling 31 | TaskEnv* getTaskEnv(Task* task); 32 | 33 | protected: 34 | void setTaskEnv(Task* task, TaskEnv_ptr env); 35 | 36 | DataBlock_ptr getTaskInputBlock(Task* task, int idx); 37 | void setTaskInputBlock(Task* task, DataBlock_ptr block, int idx); 38 | 39 | std::map queue_table; 40 | std::map tasklib_table; 41 | 42 | Platform *platform; 43 | }; 44 | } 45 | 46 | #endif 47 | -------------------------------------------------------------------------------- /manager/include/blaze/Task.h: -------------------------------------------------------------------------------- 1 | #ifndef TASK_H 2 | #define TASK_H 3 | 4 | #include "blaze/Common.h" 5 | 6 | namespace blaze { 7 | 8 | // forward declaration of 9 | template class BlazeTest; 10 | 11 | /** 12 | * Task is the base clase of an accelerator task 13 | * will be extended by user 14 | */ 15 | class Task { 16 | 17 | friend class AccAgent; 18 | friend class AppCommManager; 19 | friend class QueueManager; 20 | friend class TaskManager; 21 | 22 | template 23 | friend class BlazeTest; 24 | 25 | public: 26 | Task(int _num_args): 27 | status(NOTREADY), 28 | num_input(_num_args), 29 | num_ready(0) 30 | {; } 31 | 32 | // main function to be overwritten by accelerator implementations 33 | virtual void compute() {;} 34 | 35 | // wrapper around compute(), added indicator for task status 36 | void execute() { 37 | try { 38 | compute(); 39 | status = FINISHED; 40 | } catch (std::exception &e) { 41 | status = FAILED; 42 | throw std::runtime_error(e.what()); 43 | } 44 | } 45 | 46 | // get config for input blocks 47 | // TODO: need a way to specify general configs 48 | // or config for output block 49 | std::string getConfig(int idx, std::string key); 50 | 51 | bool isInputReady(int64_t block_id); 52 | 53 | protected: 54 | 55 | char* getOutput(int idx, int item_length, int num_items, int data_width); 56 | 57 | int getInputLength(int idx); 58 | 59 | int getInputNumItems(int idx); 60 | 61 | char* getInput(int idx); 62 | 63 | // add a configuration for a dedicated block 64 | void addConfig(int idx, std::string key, std::string val); 65 | 66 | TaskEnv* getEnv(); 67 | 68 | // a list of input blocks to its partition_id 69 | std::vector input_blocks; 70 | 71 | // list of output blocks 72 | std::vector output_blocks; 73 | 74 | // a table that maps block index to configurations 75 | std::map > config_table; 76 | 77 | // a mapping between partition_id to the input blocks 78 | std::map input_table; 79 | 80 | private: 81 | 82 | // used by AppCommManager 83 | void addInputBlock(int64_t partition_id, DataBlock_ptr block); 84 | void inputBlockReady(int64_t partition_id, DataBlock_ptr block); 85 | 86 | // push one output block to consumer 87 | // return true if there are more blocks to output 88 | bool getOutputBlock(DataBlock_ptr &block); 89 | 90 | bool isReady(); 91 | 92 | enum { 93 | NOTREADY, 94 | READY, 95 | FINISHED, 96 | FAILED, 97 | COMMITTED 98 | } status; 99 | 100 | // an unique id within each TaskQueue 101 | int task_id; 102 | 103 | // pointer to the TaskEnv 104 | TaskEnv_ptr env; 105 | 106 | // number of total input blocks 107 | int num_input; 108 | 109 | // number of input blocks that has data initialized 110 | int num_ready; 111 | }; 112 | } 113 | #endif 114 | -------------------------------------------------------------------------------- /manager/include/blaze/TaskEnv.h: -------------------------------------------------------------------------------- 1 | #ifndef TASKENV_H 2 | #define TASKENV_H 3 | 4 | #include "Common.h" 5 | 6 | namespace blaze { 7 | 8 | class TaskEnv { 9 | public: 10 | virtual DataBlock_ptr createBlock( 11 | int num_items, int item_length, int item_size, 12 | int align_width = 0, int flag = BLAZE_INPUT_BLOCK); 13 | 14 | virtual DataBlock_ptr createBlock(const DataBlock& block); 15 | }; 16 | } 17 | #endif 18 | -------------------------------------------------------------------------------- /manager/include/blaze/TaskManager.h: -------------------------------------------------------------------------------- 1 | #ifndef TASK_MANAGER_H 2 | #define TASK_MANAGER_H 3 | 4 | #include 5 | #include 6 | 7 | #include "Common.h" 8 | #include "TaskQueue.h" 9 | 10 | namespace blaze { 11 | 12 | /** 13 | * Manages a task queue for one accelerator executor 14 | */ 15 | class TaskManager 16 | : public boost::basic_lockable_adapter 17 | { 18 | 19 | public: 20 | 21 | TaskManager( 22 | Task* (*create_func)(), 23 | void (*destroy_func)(Task*), 24 | std::string _acc_id, 25 | Platform *_platform 26 | ): power(true), 27 | scheduler_idle(true), 28 | executor_idle(true), 29 | nextTaskId(0), 30 | acc_id(_acc_id), 31 | createTask(create_func), 32 | destroyTask(destroy_func), 33 | platform(_platform) 34 | {;} 35 | 36 | ~TaskManager() { 37 | power = false; 38 | task_workers.join_all(); 39 | } 40 | 41 | // create a task and return the task pointer 42 | Task_ptr create(); 43 | 44 | // enqueue a task in the corresponding application queue 45 | void enqueue(std::string app_id, Task* task); 46 | 47 | // dequeue a task from the execute queue 48 | bool popReady(Task* &task); 49 | 50 | // get best and worst cast wait time 51 | std::pair getWaitTime(Task* task); 52 | 53 | void startExecutor(); 54 | void startScheduler(); 55 | 56 | void start(); 57 | void stop(); 58 | bool isBusy(); 59 | 60 | bool isEmpty(); 61 | 62 | // experimental 63 | std::string getConfig(int idx, std::string key); 64 | 65 | private: 66 | 67 | boost::thread_group task_workers; 68 | 69 | // schedule a task from app queues to execution queue 70 | bool schedule(); 71 | 72 | // execute front task in the queue 73 | bool execute(); 74 | 75 | // Enable signal all the worker threads (scheduler, executor) 76 | bool power; 77 | 78 | // These two flag let TaskManager exits gracefully: 79 | // When power=false, but the app_queues and execution_queue 80 | // are still not empty, clear the queue before exits 81 | bool scheduler_idle; 82 | bool executor_idle; 83 | 84 | // Locate TaskEnv and for logging purpose 85 | std::string acc_id; 86 | 87 | mutable boost::atomic nextTaskId; 88 | 89 | // Task implementation loaded from user acc_impl 90 | Task* (*createTask)(); 91 | void (*destroyTask)(Task*); 92 | 93 | Platform *platform; 94 | 95 | // thread function body for scheduler and executor 96 | void do_schedule(); 97 | void do_execute(); 98 | 99 | void updateDelayModel(Task* task, int estimateTime, int realTime); 100 | 101 | // application queues mapped by application id 102 | std::map app_queues; 103 | 104 | TaskQueue execution_queue; 105 | }; 106 | 107 | const TaskManager_ptr NULL_TASK_MANAGER; 108 | } 109 | 110 | #endif 111 | -------------------------------------------------------------------------------- /manager/include/blaze/TaskQueue.h: -------------------------------------------------------------------------------- 1 | #ifndef TASK_QUEUE_H 2 | #define TASK_QUEUE_H 3 | 4 | #include 5 | 6 | #include "Common.h" 7 | 8 | namespace blaze { 9 | 10 | class TaskQueue { 11 | 12 | public: 13 | 14 | TaskQueue() {;} 15 | 16 | bool empty() { 17 | return task_queue.empty(); 18 | } 19 | 20 | bool push(Task* task) { 21 | return task_queue.push(task); 22 | } 23 | 24 | bool pop(Task* &task) { 25 | if ( empty() ) { 26 | return false; 27 | } 28 | else { 29 | bool status = task_queue.pop(task); 30 | 31 | return status; 32 | } 33 | } 34 | 35 | private: 36 | boost::lockfree::queue > task_queue; 37 | }; 38 | 39 | typedef boost::shared_ptr TaskQueue_ptr; 40 | } // namespace blaze 41 | #endif 42 | -------------------------------------------------------------------------------- /manager/include/blaze/main.h: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /manager/lib/.gitignore: -------------------------------------------------------------------------------- 1 | # Ignore everything in this directory 2 | * 3 | # Except this file 4 | !.gitignore 5 | -------------------------------------------------------------------------------- /manager/src/.gitignore: -------------------------------------------------------------------------------- 1 | *.o 2 | -------------------------------------------------------------------------------- /manager/src/AccAgent.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | #include 6 | #include 7 | 8 | #define LOG_HEADER "AccAgent" 9 | #include 10 | 11 | #include "blaze/AccAgent.h" 12 | #include "blaze/Block.h" 13 | #include "blaze/CommManager.h" 14 | #include "blaze/Platform.h" 15 | #include "blaze/PlatformManager.h" 16 | #include "blaze/TaskManager.h" 17 | #include "proto/acc_conf.pb.h" 18 | 19 | namespace blaze { 20 | 21 | AccAgent::AccAgent(const char* conf_path) { 22 | int file_handle = open(conf_path, O_RDONLY); 23 | if (file_handle < 0) { 24 | throw fileError("AccAgent cannot find configure file"); 25 | } 26 | ManagerConf_ptr conf(new ManagerConf()); 27 | conf_ = conf; 28 | google::protobuf::io::FileInputStream fin(file_handle); 29 | if (!google::protobuf::TextFormat::Parse(&fin, conf.get())) { 30 | throw fileError("AccAgent cannot parse configuration file"); 31 | } 32 | 33 | // Basic configurations 34 | //FLAGS_logtostderr = 1; 35 | FLAGS_v = conf_->verbose(); // logging 36 | int app_port = conf_->app_port(); // port for application 37 | int gam_port = conf_->gam_port(); // port for GAM 38 | 39 | //google::InitGoogleLogging(""); 40 | 41 | // Create local dir 42 | try { 43 | local_dir += "/nam-" + getUid(); 44 | if (!boost::filesystem::exists(local_dir)) { 45 | boost::filesystem::create_directories(local_dir); 46 | } 47 | DLOG(INFO) << "Set 'local_dir' to " << local_dir; 48 | } catch (boost::filesystem::filesystem_error &e) { 49 | LOG(WARNING) << "Failed to use '" << local_dir 50 | << "' as local directory, using '/tmp' instead."; 51 | } 52 | 53 | // Create a PlatformManager 54 | PlatformManager_ptr platform_manager(new PlatformManager(conf_.get())); 55 | platform_manager_ = platform_manager; 56 | 57 | LOG(INFO) << "Finish initializing AccAgent"; 58 | } 59 | 60 | Task_ptr AccAgent::createTask(std::string acc_id) { 61 | 62 | Task_ptr task; 63 | if (!platform_manager_) { 64 | DLOG(ERROR) << "Platform Manager not initialized."; 65 | return task; 66 | } 67 | Platform* platform = platform_manager_->getPlatformByAccId(acc_id); 68 | 69 | TaskManager_ref task_manager = platform_manager_->getTaskManager(acc_id); 70 | 71 | if (!task_manager.lock()) { 72 | DLOG(WARNING) << "Accelerator queue for " << acc_id 73 | << " is likely to be removed"; 74 | return task; 75 | } 76 | else { 77 | task = task_manager.lock()->create(); 78 | } 79 | return task; 80 | } 81 | 82 | void AccAgent::writeInput( 83 | Task_ptr task, 84 | std::string acc_id, 85 | void* data_ptr, 86 | int num_items, 87 | int item_length, 88 | int data_width) 89 | { 90 | if (num_items <= 0 || 91 | item_length <= 0 || 92 | data_width <= 0) 93 | { 94 | DLOG(ERROR) << num_items << ", " 95 | << item_length << ", " 96 | << data_width; 97 | throw invalidParam("Invalid input parameters"); 98 | } 99 | 100 | // create data block 101 | DataBlock_ptr block; 102 | 103 | if (num_items == 1 && item_length == 1) { 104 | if (data_width > 8) { 105 | LOG(WARNING) << "Scalar input cannot be larger than 8 bytes, " 106 | << "force it to be 8 bytes"; 107 | // since scalar variable uses a long long type in the message, 108 | // force data width to be 8 for safety 109 | data_width = 8; 110 | } 111 | // create a normal block for scalar data 112 | DataBlock_ptr new_block(new DataBlock(num_items, 113 | item_length, item_length*data_width)); 114 | block = new_block; 115 | } 116 | else { 117 | Platform* platform = platform_manager_->getPlatformByAccId(acc_id); 118 | // create a platform block for normal input 119 | block = platform->createBlock( 120 | num_items, item_length, item_length*data_width); 121 | } 122 | block->writeData(data_ptr, num_items*item_length*data_width); 123 | 124 | // add the block to task's input list, block should be ready 125 | task->addInputBlock(task->input_blocks.size(), block); 126 | 127 | if (task->isReady()) { 128 | TaskManager_ref task_manager = platform_manager_->getTaskManager(acc_id); 129 | // skip the check on task_manager for now 130 | // use acc_id instead of app_id for application queue for efficiency 131 | task_manager.lock()->enqueue(acc_id, task.get()); 132 | } 133 | } 134 | 135 | void AccAgent::readOutput( 136 | Task_ptr task, 137 | void* data_ptr, 138 | size_t data_size) 139 | { 140 | // wait on task finish 141 | while (task->status != Task::FINISHED && 142 | task->status != Task::FAILED) 143 | { 144 | boost::this_thread::sleep_for( 145 | boost::chrono::microseconds(100)); 146 | } 147 | if (task->status == Task::FINISHED) { 148 | VLOG(1) << "Task finished, starting to read output"; 149 | 150 | DataBlock_ptr block; 151 | if (!task->getOutputBlock(block)) { 152 | throw internalError("No more output blocks"); 153 | } 154 | block->readData(data_ptr, data_size); 155 | } 156 | else { 157 | throw internalError("Task failed"); 158 | } 159 | } 160 | } // namespace blaze 161 | 162 | -------------------------------------------------------------------------------- /manager/src/Admin.cpp: -------------------------------------------------------------------------------- 1 | #define LOG_HEADER "Admin" 2 | #include 3 | 4 | #include "blaze/Admin.h" 5 | 6 | namespace blaze { 7 | 8 | Admin::Admin(std::string _ip): 9 | ip_address(_ip), 10 | nam_port(1027) {;} 11 | 12 | void Admin::sendMessage(TaskMsg &msg) { 13 | 14 | // setup socket connection 15 | if (!ios || !endpoint) { 16 | ios_ptr _ios(new boost::asio::io_service); 17 | endpoint_ptr _endpoint(new boost::asio::ip::tcp::endpoint( 18 | boost::asio::ip::address::from_string(ip_address), 19 | nam_port)); 20 | 21 | ios = _ios; 22 | endpoint = _endpoint; 23 | } 24 | 25 | // create socket for connection 26 | socket_ptr sock(new boost::asio::ip::tcp::socket(*ios)); 27 | sock->connect(*endpoint); 28 | sock->set_option(boost::asio::ip::tcp::no_delay(true)); 29 | 30 | // set socket buffer size to be 4MB 31 | boost::asio::socket_base::send_buffer_size option(4*1024*1024); 32 | sock->set_option(option); 33 | 34 | send(msg, sock); 35 | 36 | // wait on reply for ACCREQUEST 37 | TaskMsg reply_msg; 38 | recv(reply_msg, sock); 39 | 40 | if (reply_msg.type() == ACCFINISH) { 41 | VLOG(1) << "Request successful"; 42 | } 43 | else { 44 | LOG(ERROR) << "Request unsucessful because: " << reply_msg.msg(); 45 | } 46 | } 47 | 48 | bool Admin::registerAcc(ManagerConf &conf) { 49 | 50 | 51 | for (int i=0; iset_acc_id(acc.id()); 64 | acc_msg->set_platform_id(platform.id()); 65 | //acc_msg->set_task_impl(readFile(acc.path())); 66 | acc_msg->set_task_impl(acc.path()); 67 | 68 | for (int k=0; kadd_param(); 71 | kval_item->set_key(kval.key()); 72 | 73 | //if (kval.key().length() > 5 && 74 | // kval.key().substr(kval.key().length()-5, 5) == "_path") 75 | //{ 76 | // kval_item->set_value(readFile(kval.value())); 77 | // DLOG(INFO) << "Setting " << kval.key() << " to contents of " 78 | // << kval.value(); 79 | //} 80 | //else 81 | { 82 | kval_item->set_value(kval.value()); 83 | DLOG(INFO) << "Setting " << kval.key() << " to " << kval.value(); 84 | } 85 | } 86 | 87 | sendMessage(req_msg); 88 | } 89 | } 90 | } 91 | 92 | bool Admin::deleteAcc(ManagerConf &conf) { 93 | 94 | for (int i=0; iset_acc_id(acc.id()); 107 | acc_msg->set_platform_id(platform.id()); 108 | 109 | sendMessage(req_msg); 110 | } 111 | } 112 | } 113 | } // namespace blaze 114 | -------------------------------------------------------------------------------- /manager/src/CommManager.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | #include 6 | #include 7 | #include 8 | #include 9 | #include 10 | 11 | #define LOG_HEADER "CommManager" 12 | #include 13 | #include 14 | #include 15 | #include 16 | #include 17 | #include 18 | 19 | #include "blaze/CommManager.h" 20 | #include "blaze/PlatformManager.h" 21 | #include "blaze/BlockManager.h" 22 | #include "blaze/TaskManager.h" 23 | 24 | #define MAX_MSGSIZE 4096 25 | 26 | namespace blaze { 27 | 28 | CommManager::CommManager( 29 | PlatformManager* _platform, 30 | std::string _address, int _port, 31 | int _max_threads): 32 | ip_address(_address), 33 | srv_port(_port), 34 | platform_manager(_platform) 35 | { 36 | // create io_service pointers 37 | ios_ptr _ios(new io_service); 38 | endpoint_ptr _endpoint(new ip::tcp::endpoint( 39 | ip::address::from_string(ip_address), 40 | srv_port)); 41 | acceptor_ptr _acceptor(new ip::tcp::acceptor(*_ios, *_endpoint)); 42 | 43 | ios = _ios; 44 | endpoint = _endpoint; 45 | acceptor = _acceptor; 46 | 47 | // start io service processing loop 48 | io_service::work work(*ios); 49 | 50 | for (int t=0; t<_max_threads; t++) 51 | { 52 | comm_threads.create_thread( 53 | boost::bind(&io_service::run, ios.get())); 54 | } 55 | 56 | // asynchronously start listening for new connections 57 | startAccept(); 58 | 59 | VLOG(2) << "Listening for new connections at " 60 | << ip_address << ":" << srv_port; 61 | } 62 | 63 | CommManager::~CommManager() { 64 | DLOG(INFO) << "Destroyer called"; 65 | ios->stop(); 66 | } 67 | 68 | void CommManager::startAccept() { 69 | socket_ptr sock(new ip::tcp::socket(*ios)); 70 | acceptor->async_accept(*sock, 71 | boost::bind(&CommManager::handleAccept, 72 | this, 73 | boost::asio::placeholders::error, 74 | sock)); 75 | } 76 | 77 | void CommManager::handleAccept( 78 | const boost::system::error_code& error, 79 | socket_ptr sock) 80 | { 81 | if (!error) { 82 | ios->post(boost::bind(&CommManager::process, this, sock)); 83 | startAccept(); 84 | } 85 | } 86 | } // namespace blaze 87 | -------------------------------------------------------------------------------- /manager/src/GAMCommManager.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | #include 6 | #include 7 | #include 8 | #include 9 | 10 | #define LOG_HEADER "GAMCommManager" 11 | #include 12 | 13 | #include "blaze/CommManager.h" 14 | #include "blaze/PlatformManager.h" 15 | #include "proto/msgGamNam.pb.h" 16 | 17 | namespace blaze { 18 | 19 | void GAMCommManager::process(socket_ptr sock) { 20 | 21 | // turn off Nagle Algorithm to improve latency 22 | sock->set_option(ip::tcp::no_delay(true)); 23 | 24 | // set socket buffer size to be 4MB 25 | socket_base::receive_buffer_size option(4*1024*1024); 26 | sock->set_option(option); 27 | 28 | Gam2NamRequest msg; 29 | try { 30 | recv(msg, sock); 31 | 32 | if (msg.type() == Gam2NamRequest::ACCNAMES) { 33 | 34 | Nam2GamAccNames reply_msg; 35 | 36 | // compile a list from platform manager 37 | std::vector > labels = 38 | platform_manager->getLabels(); 39 | 40 | // sort list to avoid permutations 41 | //std::sort(labels.begin(), labels.end()); 42 | 43 | if ((!msg.has_pull() || !msg.pull()) && 44 | labels == last_labels) 45 | { 46 | reply_msg.set_isupdated(false); 47 | } 48 | else { 49 | reply_msg.set_isupdated(true); 50 | 51 | DLOG(INFO) << "Send an updated accelerator list"; 52 | 53 | for (int i=0; iset_acc_name(labels[i].first); 56 | label->set_device_name(labels[i].second); 57 | 58 | DLOG(INFO) << "Add acc name: " << labels[i].first << 59 | " | " << labels[i].second; 60 | } 61 | last_labels = labels; 62 | } 63 | last_labels = labels; 64 | 65 | // send reply message 66 | send(reply_msg, sock); 67 | 68 | LOG_EVERY_N(INFO, 60) << "Sent 60 ACCNAMES to GAM"; 69 | } 70 | else { 71 | throw std::runtime_error("Unexpected message"); 72 | } 73 | } 74 | catch (std::exception &e) { 75 | LOG(ERROR) << "Failed to communicate with GAM: " << e.what(); 76 | } 77 | } 78 | } // namespace blaze 79 | 80 | -------------------------------------------------------------------------------- /manager/src/Makefile: -------------------------------------------------------------------------------- 1 | include ../../Makefile.config 2 | 3 | # check all variables 4 | ifeq ($(BOOST_DIR),) 5 | $(error BOOST_DIR not set properly in Makefile.config) 6 | endif 7 | ifeq ($(PROTOBUF_DIR),) 8 | $(error PROTOBUF_DIR not set properly in Makefile.config) 9 | endif 10 | ifeq ($(GLOG_DIR),) 11 | $(error PROTOBUF_DIR not set properly in Makefile.config) 12 | endif 13 | 14 | CFLAGS := -c -fPIC -std=c++0x 15 | 16 | INCLUDES := -I../include \ 17 | -I$(BOOST_DIR)/include \ 18 | -I$(PROTOBUF_DIR)/include \ 19 | -I$(GLOG_DIR)/include \ 20 | -I$(GFLAGS_DIR)/include 21 | 22 | LINK := -L../lib -lblaze \ 23 | -L$(BOOST_DIR)/lib \ 24 | -lboost_system \ 25 | -lboost_thread \ 26 | -lboost_iostreams \ 27 | -lboost_filesystem \ 28 | -lboost_regex \ 29 | -L$(PROTOBUF_DIR)/lib -lprotobuf \ 30 | -L$(GLOG_DIR)/lib -lglog \ 31 | -L$(GFLAGS_DIR)/lib -lgflags \ 32 | -lpthread -lm -Wl,--no-as-needed -ldl 33 | 34 | ifeq ($(RELEASE),) 35 | CFLAGS := $(CFLAGS) -g 36 | else 37 | CFLAGS := $(CFLAGS) -O2 -DNDEBUG 38 | endif 39 | 40 | COMPILE = $(CFLAGS) $(INCLUDES) 41 | 42 | DEPS := AccAgent.o \ 43 | Admin.o \ 44 | Block.o \ 45 | Client.o \ 46 | Common.o \ 47 | Platform.o \ 48 | Task.o \ 49 | TaskEnv.o \ 50 | BlockManager.o \ 51 | CommManager.o \ 52 | AppCommManager.o \ 53 | GAMCommManager.o \ 54 | PlatformManager.o \ 55 | TaskManager.o \ 56 | QueueManager.o \ 57 | acc_conf.pb.o \ 58 | task.pb.o \ 59 | msgGamNam.pb.o 60 | 61 | all: ../bin/acc_manager \ 62 | ../bin/acc_admin \ 63 | ../lib/libblaze.so 64 | 65 | release: 66 | $(MAKE) RELEASE=1 67 | 68 | ../lib/libblaze.so: $(DEPS) 69 | $(PP) -shared -o $@ $(DEPS) 70 | 71 | ../bin/acc_manager: ../lib/libblaze.so main.o $(LMDEPS) 72 | $(PP) -o $@ main.o $(LMDEPS) $(LINK) 73 | 74 | ../bin/acc_admin: ../lib/libblaze.so admin.o $(LMDEPS) 75 | $(PP) -o $@ admin.o $(LMDEPS) $(LINK) 76 | 77 | %.o: proto/%.cc 78 | $(PP) $(COMPILE) $< -o $@ 79 | 80 | %.o: %.cpp 81 | $(PP) $(COMPILE) $< -o $@ 82 | 83 | clean: 84 | rm -rf *.o 85 | rm -rf ../lib/libblaze.so 86 | rm -rf ../bin/acc_manager 87 | -------------------------------------------------------------------------------- /manager/src/Platform.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | #include "blaze/TaskEnv.h" 4 | #include "blaze/TaskManager.h" 5 | #include "blaze/BlockManager.h" 6 | #include "blaze/QueueManager.h" 7 | #include "blaze/Platform.h" 8 | 9 | namespace blaze { 10 | 11 | Platform::Platform(std::map &conf_table) 12 | { 13 | TaskEnv_ptr env_ptr(new TaskEnv()); 14 | env = env_ptr; 15 | 16 | // create queue 17 | QueueManager_ptr queue(new QueueManager(this)); 18 | queue_manager = queue; 19 | 20 | } 21 | 22 | // Start TaskQueues for the CPU platform 23 | // all the task queues can have simultaneous executors 24 | void Platform::addQueue(AccWorker &conf) { 25 | 26 | if (acc_table.find(conf.id()) == acc_table.end()) { 27 | acc_table.insert(std::make_pair(conf.id(), conf)); 28 | } 29 | 30 | // add a TaskManager, and the scheduler should be started 31 | queue_manager->add(conf.id(), conf.path()); 32 | 33 | // start a corresponding executor 34 | queue_manager->start(conf.id()); 35 | } 36 | 37 | void Platform::removeQueue(std::string id) { 38 | 39 | // asynchronously call queue_manager->remove(id) 40 | boost::thread executor( 41 | boost::bind(&QueueManager::remove, queue_manager.get(), id)); 42 | } 43 | 44 | // create a block object for the specific platform 45 | DataBlock_ptr Platform::createBlock( 46 | int num_items, int item_length, int item_size, 47 | int align_width, int flag) 48 | { 49 | return env->createBlock(num_items, item_length, 50 | item_size, align_width, flag); 51 | } 52 | 53 | DataBlock_ptr Platform::createBlock(const DataBlock& block) 54 | { 55 | return env->createBlock(block); 56 | } 57 | 58 | // remove a shard block from the block manager 59 | void Platform::remove(int64_t block_id) { 60 | block_manager->remove(block_id); 61 | } 62 | 63 | void Platform::createBlockManager(size_t cache_limit, size_t scratch_limit) { 64 | BlockManager_ptr bman(new BlockManager(this, cache_limit, scratch_limit)); 65 | block_manager = bman; 66 | } 67 | 68 | QueueManager* Platform::getQueueManager() { 69 | if (queue_manager) { 70 | return queue_manager.get(); 71 | } else { 72 | return NULL; 73 | } 74 | } 75 | 76 | BlockManager* Platform::getBlockManager() { 77 | if (block_manager) { 78 | return block_manager.get(); 79 | } else { 80 | return NULL; 81 | } 82 | } 83 | 84 | TaskManager_ref Platform::getTaskManager(std::string acc_id) { 85 | TaskManager_ref ret = queue_manager->get(acc_id); 86 | return ret; 87 | } 88 | 89 | // get an entry in the config_table matching the key 90 | std::string Platform::getConfig(std::string &key) { 91 | if (config_table.find(key)==config_table.end()) { 92 | return std::string(); 93 | } else { 94 | return config_table[key]; 95 | } 96 | } 97 | 98 | // get TaskEnv to pass to Task 99 | TaskEnv_ptr Platform::getEnv(std::string id) { 100 | return env; 101 | } 102 | } // namespace blaze 103 | -------------------------------------------------------------------------------- /manager/src/QueueManager.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | #include 6 | #include 7 | #include 8 | #include 9 | 10 | #define LOG_HEADER "QueueManager" 11 | #include 12 | #include 13 | 14 | #include "blaze/Task.h" 15 | #include "blaze/Block.h" 16 | #include "blaze/Platform.h" 17 | #include "blaze/TaskManager.h" 18 | #include "blaze/QueueManager.h" 19 | 20 | namespace blaze { 21 | 22 | void QueueManager::add( 23 | std::string id, 24 | std::string lib_path) 25 | { 26 | if (tasklib_table.count(id)) { 27 | LOG(WARNING) << "Cannot add Task [" << id 28 | << "] because previous Task with the same ID is not " 29 | << "successfully unloaded."; 30 | throw internalError("Task handle exists"); 31 | } 32 | void* handle = dlopen(lib_path.c_str(), RTLD_LAZY|RTLD_LOCAL); 33 | 34 | if (handle == NULL) { 35 | throw std::runtime_error(dlerror()); 36 | } 37 | // reset errors 38 | dlerror(); 39 | 40 | // load the symbols 41 | Task* (*create_func)(); 42 | void (*destroy_func)(Task*); 43 | 44 | // read the custom constructor and destructor 45 | create_func = (Task* (*)())dlsym(handle, "create"); 46 | destroy_func = (void (*)(Task*))dlsym(handle, "destroy"); 47 | 48 | const char* error = dlerror(); 49 | if (error) { 50 | throw std::runtime_error(error); 51 | } 52 | 53 | // construct the corresponding task queue 54 | TaskManager_ptr task_manager( 55 | new TaskManager(create_func, destroy_func, id, platform)); 56 | 57 | task_manager->startScheduler(); 58 | 59 | // lock before modifying queue_table 60 | boost::lock_guard guard(*this); 61 | 62 | queue_table.insert(std::make_pair(id, task_manager)); 63 | tasklib_table.insert(std::make_pair(id, handle)); 64 | 65 | LOG(INFO) << "Added a new task queue: " << id; 66 | } 67 | 68 | TaskManager_ptr QueueManager::get(std::string id) { 69 | 70 | boost::lock_guard guard(*this); 71 | if (queue_table.find(id) == queue_table.end()) { 72 | return NULL_TASK_MANAGER; 73 | } 74 | else { 75 | return queue_table[id]; 76 | } 77 | } 78 | 79 | void QueueManager::remove(std::string id) { 80 | 81 | TaskManager_ptr task_manager = get(id); 82 | 83 | if (!task_manager) { 84 | return; 85 | } 86 | 87 | this->lock(); 88 | queue_table.erase(id); 89 | this->unlock(); 90 | 91 | DLOG(INFO) << "Stopping the TaskManager for " << id; 92 | task_manager->stop(); 93 | 94 | // wait for TaskManager to exit gracefully 95 | while (task_manager->isBusy()) { 96 | boost::this_thread::sleep_for(boost::chrono::microseconds(1000)); 97 | } 98 | DLOG(INFO) << "TaskManager for " << id << " is successfully stopped"; 99 | 100 | // release the loaded library using dlclose 101 | // reset errors 102 | dlerror(); 103 | 104 | void* handle = tasklib_table[id]; 105 | 106 | dlclose(handle); 107 | 108 | const char* error = dlerror(); 109 | if (error) { 110 | DLOG(ERROR) << "Task implementation for " << id 111 | << " cannot be unloaded because:" 112 | << error; 113 | } 114 | else { 115 | DLOG(INFO) << "Task implementation for " << id << " is successfully unloaded"; 116 | 117 | // only remove item from table if dlclose is successful 118 | // otherwise prevent new accelerator with the same id 119 | // be added 120 | this->lock(); 121 | tasklib_table.erase(id); 122 | this->unlock(); 123 | } 124 | } 125 | 126 | TaskEnv* QueueManager::getTaskEnv(Task* task) { 127 | return task->getEnv(); 128 | } 129 | 130 | void QueueManager::setTaskEnv(Task* task, TaskEnv_ptr env) { 131 | task->env = env; 132 | } 133 | 134 | DataBlock_ptr QueueManager::getTaskInputBlock(Task *task, int idx) { 135 | if (idx < task->input_blocks.size() && 136 | task->input_table.find(task->input_blocks[idx]) 137 | != task->input_table.end()) 138 | { 139 | return task->input_table[task->input_blocks[idx]]; 140 | } else { 141 | return NULL_DATA_BLOCK; 142 | } 143 | } 144 | 145 | void QueueManager::setTaskInputBlock( 146 | Task *task, 147 | DataBlock_ptr block, 148 | int idx) 149 | { 150 | if (idx < task->input_blocks.size()) { 151 | int64_t block_id = task->input_blocks[idx]; 152 | DLOG(INFO) << "Reset task input block " << block_id; 153 | task->inputBlockReady(block_id, block); 154 | } 155 | } 156 | 157 | // Start TaskQueues for the CPU platform 158 | // all the task queues can have simultaneous executors 159 | void QueueManager::start(std::string id) { 160 | 161 | // get the reference to the task queue 162 | TaskManager_ptr task_manager = get(id); 163 | if (task_manager) { 164 | task_manager->startExecutor(); 165 | } 166 | else { 167 | LOG(ERROR) << "Cannot start executor for " << id; 168 | } 169 | } 170 | 171 | } // namespace blaze 172 | 173 | -------------------------------------------------------------------------------- /manager/src/TaskEnv.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | 6 | #include "blaze/Block.h" 7 | #include "blaze/TaskEnv.h" 8 | 9 | namespace blaze { 10 | 11 | DataBlock_ptr TaskEnv::createBlock( 12 | int num_items, 13 | int item_length, 14 | int item_size, 15 | int align_width, 16 | int flag) 17 | { 18 | DataBlock_ptr block(new DataBlock( 19 | num_items, item_length, item_size, align_width, flag)); 20 | return block; 21 | } 22 | 23 | DataBlock_ptr TaskEnv::createBlock(const DataBlock& block) { 24 | DataBlock_ptr bp(new DataBlock(block)); 25 | return bp; 26 | } 27 | 28 | } 29 | -------------------------------------------------------------------------------- /manager/src/admin.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | #define LOG_HEADER "Admin" 5 | #include 6 | 7 | // use flexlm 8 | #ifdef USELICENSE 9 | #include "license.h" 10 | #endif 11 | 12 | #include "blaze/Admin.h" 13 | 14 | using namespace blaze; 15 | 16 | int main(int argc, char** argv) { 17 | 18 | google::InitGoogleLogging(argv[0]); 19 | 20 | FLAGS_logtostderr = 1; 21 | FLAGS_v = 1; 22 | 23 | srand(time(NULL)); 24 | 25 | if (argc < 3) { 26 | printf("USAGE: %s [NAM_IP]\n", argv[0]); 27 | return -1; 28 | } 29 | 30 | std::string conf_path(argv[2]); 31 | int file_handle = open(conf_path.c_str(), O_RDONLY); 32 | 33 | if (file_handle < 0) { 34 | printf("cannot find configure file: %s\n", 35 | argv[1]); 36 | return -1; 37 | } 38 | 39 | ManagerConf *conf = new ManagerConf(); 40 | google::protobuf::io::FileInputStream fin(file_handle); 41 | 42 | 43 | if (!google::protobuf::TextFormat::Parse(&fin, conf)) { 44 | LOG(FATAL) << "cannot parse configuration from " << argv[1]; 45 | } 46 | 47 | Admin admin; 48 | 49 | if (strcmp(argv[1], "d")) { 50 | admin.registerAcc(*conf); 51 | } 52 | else { 53 | admin.deleteAcc(*conf); 54 | } 55 | 56 | return 0; 57 | } 58 | -------------------------------------------------------------------------------- /manager/src/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | #include 6 | #include 7 | #include 8 | #include 9 | #include 10 | #include 11 | #include 12 | 13 | #include 14 | #include 15 | 16 | #define LOG_HEADER "main" 17 | #include 18 | #include 19 | 20 | #include "blaze/CommManager.h" 21 | #include "blaze/PlatformManager.h" 22 | #include "blaze/QueueManager.h" 23 | #include "blaze/BlockManager.h" 24 | #include "blaze/TaskManager.h" 25 | 26 | using namespace blaze; 27 | 28 | int main(int argc, char** argv) { 29 | 30 | // Initialize Google Flags and Logs 31 | gflags::SetUsageMessage(argv[0]); 32 | gflags::ParseCommandLineFlags(&argc, &argv, true); 33 | google::InitGoogleLogging(argv[0]); 34 | 35 | srand(time(NULL)); 36 | 37 | if (argc < 2) { 38 | printf("USAGE: %s \n", argv[0]); 39 | return -1; 40 | } 41 | 42 | std::string conf_path(argv[1]); 43 | int file_handle = open(conf_path.c_str(), O_RDONLY); 44 | 45 | if (file_handle < 0) { 46 | printf("cannot find configure file: %s\n", 47 | argv[1]); 48 | return -1; 49 | } 50 | 51 | ManagerConf *conf = new ManagerConf(); 52 | google::protobuf::io::FileInputStream fin(file_handle); 53 | 54 | if (!google::protobuf::TextFormat::Parse(&fin, conf)) { 55 | LOG(FATAL) << "cannot parse configuration from " << argv[1]; 56 | } 57 | 58 | // configurations 59 | FLAGS_v = conf->verbose(); // logging 60 | int app_port = conf->app_port(); // port for application 61 | int gam_port = conf->gam_port(); // port for GAM 62 | local_dir = conf->local_dir(); // local dir for temp files 63 | 64 | // create local dir 65 | try { 66 | local_dir += "/nam-" + getUid(); 67 | if (!boost::filesystem::exists(local_dir)) { 68 | boost::filesystem::create_directories(local_dir); 69 | } 70 | DLOG(INFO) << "Set 'local_dir' to " << local_dir; 71 | } catch (boost::filesystem::filesystem_error &e) { 72 | LOG(ERROR) << "Failed to use '" << local_dir 73 | << "' as local directory, using '/tmp' instead."; 74 | } 75 | 76 | // setup PlatformManager 77 | PlatformManager platform_manager(conf); 78 | 79 | // check all network interfaces on this computer, and 80 | // open a communicator on each interface using the same port 81 | struct ifaddrs* ifAddrStruct = NULL; 82 | getifaddrs(&ifAddrStruct); 83 | 84 | // hold all pointers to the communicator 85 | std::vector > comm_pool; 86 | 87 | for (struct ifaddrs* ifa = ifAddrStruct; 88 | ifa != NULL; 89 | ifa = ifa->ifa_next) 90 | { 91 | if (!ifa->ifa_addr) { 92 | continue; 93 | } 94 | // check if is a valid IP4 Address 95 | if (ifa->ifa_addr->sa_family == AF_INET) { 96 | 97 | // obtain the ip address as a string 98 | void* tmpAddrPtr = &((struct sockaddr_in *)ifa->ifa_addr)->sin_addr; 99 | char addressBuffer[INET_ADDRSTRLEN]; 100 | 101 | inet_ntop(AF_INET, tmpAddrPtr, addressBuffer, INET_ADDRSTRLEN); 102 | 103 | std::string ip_addr(addressBuffer); 104 | 105 | try { 106 | // create communicator for GAM 107 | boost::shared_ptr comm_gam( new GAMCommManager( 108 | &platform_manager, 109 | ip_addr, gam_port)); 110 | 111 | // create communicator for applications 112 | // it will start listening for new connections automatically 113 | boost::shared_ptr comm( new AppCommManager( 114 | &platform_manager, 115 | ip_addr, app_port)); 116 | 117 | LOG(INFO) << "Start listening " << ip_addr << " on port " << 118 | app_port << " and " << gam_port; 119 | 120 | // push the communicator pointer to pool to avoid object 121 | // being destroyed out of context 122 | comm_pool.push_back(comm); 123 | comm_pool.push_back(comm_gam); 124 | } 125 | catch (boost::system::system_error &e) { 126 | LOG(WARNING) << "Failed to start communication manager on " 127 | << ip_addr << ", because: " << e.what(); 128 | } 129 | } 130 | } 131 | if (comm_pool.empty()) { 132 | LOG(ERROR) << "Failed to start communication on any interface, exiting."; 133 | return 1; 134 | } 135 | 136 | while (1) { 137 | boost::this_thread::sleep_for(boost::chrono::seconds(60)); 138 | } 139 | return 0; 140 | } 141 | -------------------------------------------------------------------------------- /manager/src/proto/.gitignore: -------------------------------------------------------------------------------- 1 | # Ignore everything in this directory 2 | * 3 | # Except this file 4 | !.gitignore 5 | -------------------------------------------------------------------------------- /manager/test/.gitignore: -------------------------------------------------------------------------------- 1 | *.csv 2 | *.html 3 | -------------------------------------------------------------------------------- /manager/test/Makefile: -------------------------------------------------------------------------------- 1 | CFLAGS := -g 2 | OBJS := src/main.o \ 3 | src/AppClients.o \ 4 | src/BlockTests.o \ 5 | src/ClientTests.o \ 6 | src/ConfigTests.o 7 | 8 | DST := bin/test_app 9 | 10 | include common.mk 11 | 12 | test: 13 | LD_LIBRARY_PATH=$(BLAZE_HOME)/manager/lib:$(LD_LIBRARY_PATH) \ 14 | GLOG_log_dir="logs" \ 15 | GLOG_stderrthreshold=3 \ 16 | GLOG_v=3 \ 17 | ./$(DST) 18 | 19 | tasks: 20 | $(MAKE) -C tasks 21 | 22 | $(DST): $(OBJS) 23 | $(PP) -o $@ $(OBJS) $(LINK) 24 | 25 | .PHONY: test tasks 26 | -------------------------------------------------------------------------------- /manager/test/bin/.gitignore: -------------------------------------------------------------------------------- 1 | # Ignore everything in this directory 2 | * 3 | # Except this file 4 | !.gitignore 5 | -------------------------------------------------------------------------------- /manager/test/common.mk: -------------------------------------------------------------------------------- 1 | ifeq ($(BLAZE_HOME),) 2 | $(error BLAZE_HOME is not set) 3 | endif 4 | ifeq ("$(wildcard $(BLAZE_HOME)/manager)","") 5 | $(error BLAZE_HOME is not set correctly) 6 | endif 7 | 8 | # need to setup BLAZE_HOME correctly 9 | include $(BLAZE_HOME)/Makefile.config 10 | 11 | MANAGER_DIR = $(BLAZE_HOME)/manager 12 | 13 | # check all variables 14 | ifeq ($(BOOST_DIR),) 15 | $(error BOOST_DIR is not set properly in Makefile.config) 16 | endif 17 | ifeq ($(PROTOBUF_DIR),) 18 | $(error PROTOBUF_DIR is not set properly in Makefile.config) 19 | endif 20 | ifeq ($(GLOG_DIR),) 21 | $(error GLOG_DIR is not set properly in Makefile.config) 22 | endif 23 | ifeq ($(GTEST_DIR),) 24 | $(error GTEST_DIR is not set properly in Makefile.config) 25 | endif 26 | 27 | # binaries 28 | PP=g++ 29 | CC=gcc 30 | CC=ar 31 | RM=rm 32 | ECHO=echo 33 | MAKE=make 34 | 35 | CFLAGS := -c -fPIC -std=c++0x $(CFLAGS) 36 | 37 | INCLUDES := -I$(BLAZE_HOME)/manager/include \ 38 | -I$(BOOST_DIR)/include \ 39 | -I$(PROTOBUF_DIR)/include \ 40 | -I$(GLOG_DIR)/include \ 41 | -I$(GFLAGS_DIR)/include \ 42 | -I$(GTEST_DIR)/include \ 43 | $(INCLUDES) 44 | 45 | COMPILE := $(CFLAGS) $(INCLUDES) 46 | 47 | LINK := -L$(BLAZE_HOME)/manager/lib -lblaze \ 48 | -L$(BOOST_DIR)/lib \ 49 | -lboost_system \ 50 | -lboost_thread \ 51 | -lboost_iostreams \ 52 | -lboost_filesystem \ 53 | -lboost_regex \ 54 | -L$(PROTOBUF_DIR)/lib -lprotobuf \ 55 | -L$(GLOG_DIR)/lib -lglog \ 56 | -L$(GFLAGS_DIR)/lib -lgflags \ 57 | -L$(GTEST_DIR)/build -lgtest \ 58 | -lpthread -lm -ldl \ 59 | $(LINK) 60 | 61 | all: $(DST) 62 | 63 | %.o: %.cpp 64 | $(PP) $(COMPILE) $< -o $@ 65 | 66 | clean: 67 | $(RM) -rf $(OBJS) 68 | $(RM) -rf $(DST) 69 | 70 | .PHONY: all clean 71 | -------------------------------------------------------------------------------- /manager/test/logs/.gitignore: -------------------------------------------------------------------------------- 1 | # Ignore everything in this directory 2 | * 3 | # Except this file 4 | !.gitignore 5 | -------------------------------------------------------------------------------- /manager/test/python/.gitignore: -------------------------------------------------------------------------------- 1 | task_pb2.py 2 | acc_conf_pb2.py 3 | -------------------------------------------------------------------------------- /manager/test/python/blaze_client.py: -------------------------------------------------------------------------------- 1 | import sys, socket 2 | import struct 3 | import acc_conf_pb2 4 | import task_pb2 5 | import logging 6 | import array 7 | from google.protobuf import text_format as _text_format 8 | 9 | class blaze_client: 10 | ip = "127.0.0.1" 11 | port = 1027 12 | sock = [] 13 | logger = [] 14 | buffer_size = 4*1024*1024 15 | 16 | def __init__(self, ip): 17 | 18 | self.ip = ip 19 | 20 | # setup socket 21 | self.sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) 22 | self.sock.setsockopt(socket.IPPROTO_TCP, socket.TCP_NODELAY, True) 23 | self.sock.setsockopt(socket.SOL_SOCKET, socket.SO_SNDBUF, self.buffer_size) 24 | 25 | # logging 26 | FORMAT = '%(asctime)-15s %(message)s' 27 | logging.basicConfig(format=FORMAT) 28 | self.logger = logging.getLogger() 29 | self.logger.setLevel(logging.INFO) 30 | 31 | def send_msg(self, sock, msg): 32 | # serialize msg to bytes 33 | msg_bytes = msg.SerializeToString() 34 | 35 | # send the total size 36 | size = len(msg_bytes) 37 | size_str = struct.pack('= 1e-6) { 52 | return false; 53 | } 54 | } 55 | return true; 56 | } 57 | 58 | bool runLoopBack(int data_size) { 59 | // prepare input 60 | TestClient client(1, 1); 61 | 62 | double* input_ptr = (double*)client.createInput(0, 1, data_size, sizeof(double), BLAZE_INPUT); 63 | 64 | // setup input with random data 65 | for (int k=0; k= 1e-6) { 76 | return false; 77 | } 78 | } 79 | return true; 80 | } 81 | 82 | bool runDelay(int data_size) { 83 | // prepare input 84 | TestClient client(1, 0); 85 | 86 | double* input_ptr = (double*)client.createInput(0, 1, data_size, sizeof(double), BLAZE_INPUT); 87 | 88 | // setup input with random data 89 | for (int k=0; k comm( new AppCommManager( 26 | &platform_manager, "127.0.0.1", app_port)); 27 | 28 | TaskMsg req_msg; 29 | 30 | // test acc register 31 | req_msg.set_type(ACCREGISTER); 32 | 33 | AccMsg* acc_msg = req_msg.mutable_acc(); 34 | 35 | acc_msg->set_acc_id(acc_id); 36 | acc_msg->set_platform_id(platform_id); 37 | acc_msg->set_task_impl(pathToLoopBack); 38 | 39 | try { 40 | comm->handleAccRegister(req_msg); 41 | } catch (std::exception &e) { 42 | ASSERT_EQ(true, false) << "Caught unexpected exception: " << e.what(); 43 | } 44 | 45 | // accelerator should be registered 46 | ASSERT_EQ(true, platform_manager.accExists(acc_id)); 47 | try { 48 | ASSERT_EQ(true, runLoopBack()); 49 | } catch (cpuCalled &e) { 50 | ASSERT_EQ(false, true) << "Client error"; 51 | } 52 | 53 | // try register another one 54 | acc_msg->set_task_impl(pathToArrayTest); 55 | try { 56 | comm->handleAccRegister(req_msg); 57 | } catch (std::exception &e) { 58 | ASSERT_EQ(true, true); 59 | } 60 | // accelerator should not change 61 | try { 62 | ASSERT_EQ(true, runLoopBack()); 63 | } catch (cpuCalled &e) { 64 | ASSERT_EQ(false, true) << "Client error"; 65 | } 66 | 67 | // test acc delete 68 | req_msg.set_type(ACCDELETE); 69 | 70 | try { 71 | comm->handleAccDelete(req_msg); 72 | } catch (std::exception &e) { 73 | ASSERT_EQ(true, false) << "Caught unexpected exception: " << e.what(); 74 | } 75 | ASSERT_EQ(false, platform_manager.accExists(acc_id)); 76 | try { 77 | runLoopBack(); 78 | } catch (cpuCalled &e) { 79 | // should catch exception here 80 | ASSERT_EQ(true, true); 81 | } 82 | 83 | // test acc register again for ArrayTest 84 | req_msg.set_type(ACCREGISTER); 85 | 86 | try { 87 | comm->handleAccRegister(req_msg); 88 | } catch (std::exception &e) { 89 | ASSERT_EQ(true, false) << "Caught unexpected exception: " << e.what(); 90 | } 91 | // accelerator should be registered as ArrayTest 92 | ASSERT_EQ(true, platform_manager.accExists(acc_id)); 93 | try { 94 | ASSERT_EQ(true, runArrayTest()); 95 | } catch (cpuCalled &e) { 96 | ASSERT_EQ(false, true) << "Client error"; 97 | } 98 | } 99 | 100 | } // namespace blaze 101 | -------------------------------------------------------------------------------- /manager/test/src/TestCommon.h: -------------------------------------------------------------------------------- 1 | #ifndef TEST_COMMON_H 2 | #define TEST_COMMON_H 3 | 4 | #include 5 | #include 6 | 7 | #include 8 | #include 9 | #include 10 | 11 | #include 12 | #include 13 | #include 14 | 15 | #include "blaze/Common.h" 16 | 17 | namespace blaze { 18 | 19 | // custom exceptions 20 | class cpuCalled : public std::runtime_error { 21 | public: 22 | explicit cpuCalled(const std::string& what_arg): 23 | std::runtime_error(what_arg) {;} 24 | }; 25 | 26 | class BlockTests : public ::testing::Test { 27 | protected: 28 | BlockTests(); 29 | virtual void SetUp(); 30 | virtual void TearDown(); 31 | 32 | Platform_ptr platform; 33 | BlockManager* bman; 34 | }; 35 | 36 | class ClientTests : public ::testing::Test { 37 | protected: 38 | ClientTests() { } 39 | }; 40 | 41 | class ConfigTests : public ::testing::Test { 42 | protected: 43 | ConfigTests() { } 44 | }; 45 | 46 | // worker function to run app tests using Client 47 | bool runArrayTest(); 48 | bool runLoopBack(int data_size = 1024); 49 | bool runDelay(int data_size = 1024); 50 | 51 | // global variables 52 | static int app_port = 7777; 53 | static std::string platform_dir = "../../platforms"; 54 | static std::string nv_opencl_path = platform_dir + "/nv_opencl/nv_opencl.so"; 55 | static std::string lnx_opencl_path = platform_dir + "/xlnx_opencl/xlnx_opencl.so"; 56 | static std::string pathToArrayTest = "./tasks/cpu/arrayTest/arrayTest.so"; 57 | static std::string pathToLoopBack = "./tasks/cpu/loopBack/loopBack.so"; 58 | 59 | } 60 | 61 | #endif 62 | -------------------------------------------------------------------------------- /manager/test/src/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | #include "TestCommon.h" 5 | 6 | int main(int argc, char **argv) { 7 | ::testing::InitGoogleTest(&argc, argv); 8 | google::InitGoogleLogging(argv[0]); 9 | return RUN_ALL_TESTS(); 10 | } 11 | -------------------------------------------------------------------------------- /manager/test/tasks/Makefile: -------------------------------------------------------------------------------- 1 | SUBDIRS = cpu 2 | 3 | all: $(SUBDIRS) 4 | 5 | clean: 6 | for dir in $(SUBDIRS); do \ 7 | $(MAKE) -C $$dir $@; \ 8 | done 9 | 10 | $(SUBDIRS): 11 | $(MAKE) -C $@ 12 | 13 | .PHONY: all clean $(SUBDIRS) 14 | -------------------------------------------------------------------------------- /manager/test/tasks/cpu/Makefile: -------------------------------------------------------------------------------- 1 | #include common.mk 2 | 3 | SUBDIRS = loopBack \ 4 | arrayTest \ 5 | delay 6 | 7 | all: $(SUBDIRS) 8 | 9 | clean: 10 | for dir in $(SUBDIRS); do \ 11 | $(MAKE) -C $$dir $@; \ 12 | done 13 | 14 | $(SUBDIRS): 15 | $(MAKE) -C $@ 16 | 17 | .PHONY: all clean $(SUBDIRS) 18 | -------------------------------------------------------------------------------- /manager/test/tasks/cpu/arrayTest/Makefile: -------------------------------------------------------------------------------- 1 | DIRNAME := $(notdir $(patsubst %/,%,$(shell pwd))) 2 | DST := $(DIRNAME).so 3 | OBJS := $(DIRNAME).o 4 | include ../common.mk 5 | 6 | -------------------------------------------------------------------------------- /manager/test/tasks/cpu/arrayTest/arrayTest.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | #include "blaze/Task.h" 5 | 6 | using namespace blaze; 7 | 8 | class ArrayTest : public Task { 9 | public: 10 | 11 | // extends the base class constructor 12 | // to indicate how many input blocks 13 | // are required 14 | ArrayTest(): Task(2) {;} 15 | 16 | // overwrites the compute function 17 | virtual void compute() { 18 | 19 | // get input data dimensions 20 | int total_length = getInputLength(0); 21 | int num_vectors = getInputNumItems(0); 22 | int vector_length = total_length / num_vectors; 23 | 24 | // get the pointer to input/output data 25 | double* a = (double*)getInput(0); 26 | double* b = (double*)getInput(1); 27 | double* c = (double*)getOutput(0, 28 | vector_length, num_vectors, sizeof(double)); 29 | 30 | // perform computation 31 | // c[i] = a[i] + b 32 | for (int i=0; i 2 | #include 3 | #include 4 | #include 5 | 6 | #include "blaze/Task.h" 7 | using namespace blaze; 8 | 9 | class Delay : public Task { 10 | public: 11 | 12 | // extends the base class constructor 13 | // to indicate how many input blocks 14 | // are required 15 | Delay(): Task(1) {;} 16 | 17 | // overwrites the compute function 18 | virtual void compute() { 19 | sleep(1); 20 | } 21 | }; 22 | 23 | extern "C" Task* create() { 24 | return new Delay(); 25 | } 26 | 27 | extern "C" void destroy(Task* p) { 28 | delete p; 29 | } 30 | -------------------------------------------------------------------------------- /manager/test/tasks/cpu/loopBack/Makefile: -------------------------------------------------------------------------------- 1 | DIRNAME := $(notdir $(patsubst %/,%,$(shell pwd))) 2 | DST := $(DIRNAME).so 3 | OBJS := $(DIRNAME).o 4 | include ../common.mk 5 | 6 | -------------------------------------------------------------------------------- /manager/test/tasks/cpu/loopBack/loopBack.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | #include 6 | #include 7 | #include 8 | #include 9 | 10 | #include "blaze/Task.h" 11 | using namespace blaze; 12 | 13 | class LB : public Task { 14 | public: 15 | 16 | // extends the base class constructor 17 | // to indicate how many input blocks 18 | // are required 19 | LB(): Task(1) {;} 20 | 21 | // overwrites the compute function 22 | virtual void compute() { 23 | 24 | // get input data length 25 | int data_length = getInputLength(0); 26 | 27 | if (data_length == 0) { 28 | throw std::runtime_error("Invalid data length"); 29 | } 30 | 31 | // get the pointer to input/output data 32 | double* src_data = (double*)getInput(0); 33 | double* dst_data = (double*)getOutput(0, data_length, 1, sizeof(double)); 34 | 35 | if (!src_data || !dst_data) { 36 | throw std::runtime_error("Cannot get data pointers"); 37 | } 38 | memcpy(dst_data, src_data, data_length*sizeof(double)); 39 | } 40 | }; 41 | 42 | extern "C" Task* create() { 43 | return new LB(); 44 | } 45 | 46 | extern "C" void destroy(Task* p) { 47 | delete p; 48 | } 49 | -------------------------------------------------------------------------------- /platforms/Makefile: -------------------------------------------------------------------------------- 1 | SUBDIRS := nv_opencl 2 | 3 | all: $(SUBDIRS) 4 | 5 | clean: 6 | for dir in $(SUBDIRS); do \ 7 | $(MAKE) -C $$dir $@; \ 8 | done 9 | 10 | $(SUBDIRS): 11 | $(MAKE) -C $@ 12 | 13 | .PHONY: all clean $(SUBDIRS) 14 | -------------------------------------------------------------------------------- /platforms/intel_aal/.gitignore: -------------------------------------------------------------------------------- 1 | *.o 2 | *.so 3 | -------------------------------------------------------------------------------- /platforms/intel_aal/AALBlock.cpp: -------------------------------------------------------------------------------- 1 | #include "AALBlock.h" 2 | 3 | namespace blaze { 4 | 5 | void AALBlock::alloc(int64_t _size) { 6 | ICCIAFU* service = env->getContext(); 7 | printf("allocating AAL Block of size %d\n", _size); 8 | 9 | if (!allocated) { 10 | 11 | service->WorkspaceAllocate(_size, TransactionID()); 12 | 13 | m_Sem.Wait(); 14 | 15 | if (m_Status != true) { 16 | throw std::runtime_error("Failed to create AAL block"); 17 | } 18 | size = _size; 19 | 20 | allocated = true; 21 | } 22 | } 23 | 24 | void AALBlock::writeData(void* src, size_t _size) { 25 | 26 | if (allocated) { 27 | 28 | if (_size > size) { 29 | throw std::runtime_error("not enough space"); 30 | } 31 | printf("start memcpy for %lx\n", data_virt); 32 | memcpy(data_virt, src, _size); 33 | ready = true; 34 | } 35 | else { 36 | throw std::runtime_error("Block memory not allocated"); 37 | } 38 | } 39 | 40 | void AALBlock::writeData(void* src, size_t _size, size_t offset) { 41 | 42 | if (allocated) { 43 | if (offset+_size > size) { 44 | throw std::runtime_error("Exists block size"); 45 | } 46 | 47 | // TODO: check data width of data_virt 48 | memcpy(data_virt+offset, src, _size); 49 | 50 | if (offset + _size == size) { 51 | ready = true; 52 | } 53 | } 54 | else { 55 | throw std::runtime_error("Block memory not allocated"); 56 | } 57 | } 58 | 59 | // write data to an array 60 | void AALBlock::readData(void* dst, size_t _size) { 61 | if (allocated) { 62 | if (_size > size) { 63 | throw std::runtime_error("not enough space"); 64 | } 65 | memcpy(dst, data_virt, _size); 66 | } 67 | else { 68 | throw std::runtime_error("Block memory not allocated"); 69 | } 70 | } 71 | 72 | // 73 | void AALBlock::OnWorkspaceAllocated(TransactionID const &TranID, 74 | btVirtAddr WkspcVirt, 75 | btPhysAddr WkspcPhys, 76 | btWSSize WkspcSize) 77 | { 78 | AutoLock(this); 79 | 80 | data_virt = WkspcVirt; 81 | data_phys = WkspcPhys; 82 | 83 | printf("Workspace allocated\n"); 84 | 85 | m_Sem.Post(1); 86 | } 87 | 88 | void AALBlock::OnWorkspaceAllocateFailed(const IEvent &rEvent) 89 | { 90 | IExceptionTransactionEvent * pExEvent = 91 | dynamic_ptr(iidExTranEvent, rEvent); 92 | ERR("OnWorkspaceAllocateFailed"); 93 | ERR(pExEvent->Description()); 94 | 95 | m_Status = false; 96 | m_Sem.Post(1); 97 | } 98 | 99 | void AALBlock::OnWorkspaceFreeFailed(const IEvent &rEvent) 100 | { 101 | IExceptionTransactionEvent * pExEvent = dynamic_ptr(iidExTranEvent, rEvent); 102 | ERR("OnWorkspaceFreeFailed"); 103 | ERR(pExEvent->Description()); 104 | m_Status = false; 105 | m_Sem.Post(1); 106 | } 107 | 108 | }; // namespace blaze 109 | -------------------------------------------------------------------------------- /platforms/intel_aal/AALBlock.h: -------------------------------------------------------------------------------- 1 | #ifndef AALBLOCK_H 2 | #define AALBLOCK_H 3 | 4 | #include 5 | #include 6 | #include 7 | #include 8 | 9 | #include 10 | #include 11 | 12 | #include 13 | #include 14 | #include 15 | #include 16 | 17 | #include "RuntimeClient.h" 18 | #include "Block.h" 19 | #include "AALEnv.h" 20 | 21 | namespace blaze { 22 | 23 | class AALBlock : public DataBlock, 24 | public CAASBase, 25 | public ICCIClient 26 | { 27 | 28 | public: 29 | // create a single output elements 30 | AALBlock(AALEnv* _env, size_t _length, size_t _size): 31 | env(_env), 32 | m_Status(true) 33 | { 34 | SetInterface(iidCCIClient, dynamic_cast(this)); 35 | size = _size; 36 | length = _length; 37 | ready = false; 38 | 39 | try { 40 | alloc(size); 41 | } 42 | catch (std::exception &e) { 43 | throw e; 44 | } 45 | } 46 | 47 | AALBlock(AALEnv* _env): 48 | DataBlock(), 49 | env(_env), 50 | m_Status(true) 51 | { 52 | //SetInterface(iidCCIClient, dynamic_cast(this)); 53 | } 54 | 55 | AALBlock(AALEnv* _env, DataBlock *block): env(_env) 56 | { 57 | //SetInterface(iidCCIClient, dynamic_cast(this)); 58 | length = block->getLength(); 59 | size = block->getSize(); 60 | num_items = block->getNumItems(); 61 | m_Status = true; 62 | 63 | if (block->isAllocated()) { 64 | try { 65 | alloc(size); 66 | } 67 | catch (std::exception &e) { 68 | throw e; 69 | } 70 | } 71 | // if ready, copy the data over 72 | if (block->isReady()) { 73 | writeData((void*)block->getData(), size); 74 | ready = true; 75 | } 76 | } 77 | 78 | ~AALBlock() { 79 | ICCIAFU* service = env->getContext(); 80 | if (allocated) { 81 | service->WorkspaceFree(data_virt, TransactionID()); 82 | m_Sem.Wait(); 83 | 84 | if (!m_Status) { 85 | printf("freeing block failed\n"); 86 | } 87 | } 88 | } 89 | 90 | virtual void alloc(int64_t _size); 91 | 92 | // copy data from an array 93 | virtual void writeData(void* src, size_t _size); 94 | 95 | // copy data from an array with offset 96 | virtual void writeData(void* src, size_t _size, size_t offset); 97 | 98 | // write data to an array 99 | virtual void readData(void* dst, size_t size); 100 | 101 | virtual char* getData() { 102 | 103 | if (allocated) { 104 | // this is a reinterpretive cast from cl_mem* to char* 105 | return (char*)data_phys; 106 | } 107 | else { 108 | return NULL; 109 | } 110 | } 111 | 112 | AAL_Workspace getWorkspace() { 113 | AAL_Workspace res; 114 | res.virt = data_virt; 115 | res.phys = data_phys; 116 | res.size = size; 117 | 118 | return res; 119 | } 120 | 121 | // 122 | virtual void OnWorkspaceAllocated(TransactionID const &TranID, 123 | btVirtAddr WkspcVirt, 124 | btPhysAddr WkspcPhys, 125 | btWSSize WkspcSize); 126 | 127 | virtual void OnWorkspaceAllocateFailed(const IEvent &Event); 128 | 129 | virtual void OnWorkspaceFreed(TransactionID const &TranID) {;} 130 | 131 | virtual void OnWorkspaceFreeFailed(const IEvent &Event); 132 | // 133 | 134 | private: 135 | 136 | btVirtAddr data_virt; // workspace virtual address. 137 | btPhysAddr data_phys; // workspace physical address. 138 | 139 | CSemaphore m_Sem; // For synchronizing with the AAL runtime. 140 | btBool m_Status; 141 | 142 | AALEnv *env; 143 | }; 144 | 145 | typedef boost::shared_ptr AALBlock_ptr; 146 | } 147 | 148 | #endif 149 | -------------------------------------------------------------------------------- /platforms/intel_aal/AALEnv.h: -------------------------------------------------------------------------------- 1 | #ifndef AALENV_H 2 | #define AALENV_H 3 | 4 | #include 5 | #include 6 | #include 7 | #include 8 | #include 9 | #include 10 | 11 | #include 12 | #include 13 | #include 14 | #include 15 | 16 | #include "TaskEnv.h" 17 | 18 | using namespace AAL; 19 | 20 | namespace blaze { 21 | 22 | typedef struct { 23 | btVirtAddr virt; 24 | btPhysAddr phys; 25 | btWSSize size; 26 | } AAL_Workspace; 27 | 28 | class AALPlatform; 29 | 30 | class AALEnv : public TaskEnv 31 | { 32 | friend class AALPlatform; 33 | 34 | public: 35 | AALEnv(): 36 | TaskEnv(), 37 | context(NULL) 38 | {;} 39 | 40 | ICCIAFU* getContext() { 41 | return context; 42 | } 43 | 44 | AAL_Workspace getDSM() { 45 | return dsm; 46 | } 47 | 48 | private: 49 | ICCIAFU *context; 50 | AAL_Workspace dsm; 51 | }; 52 | } 53 | 54 | #endif 55 | -------------------------------------------------------------------------------- /platforms/intel_aal/AALPlatform.cpp: -------------------------------------------------------------------------------- 1 | #include "AALPlatform.h" 2 | 3 | namespace blaze { 4 | 5 | AALPlatform::AALPlatform() { 6 | // create a AAL runtime client first 7 | m_runtimeClient = new RuntimeClient(); 8 | if(!m_runtimeClient->isOK()){ 9 | throw std::runtime_error("Runtime Failed to Start"); 10 | } 11 | 12 | SetSubClassInterface(iidServiceClient, dynamic_cast(this)); 13 | SetInterface(iidCCIClient, dynamic_cast(this)); 14 | m_Sem.Create(0, 1); 15 | m_Status = true; 16 | 17 | env = new AALEnv(); 18 | } 19 | 20 | void AALPlatform::setupAcc(AccWorker &conf) { 21 | 22 | std::string afu_name; 23 | std::string afu_id; 24 | std::string afu_location; 25 | 26 | for (int i=0; igetRuntime()->allocService(dynamic_cast(this), Manifest); 73 | m_Sem.Wait(); 74 | 75 | if (m_Status != true) { 76 | throw std::runtime_error("failed to allocate AAL Service"); 77 | } 78 | 79 | ((AALEnv*)env)->context = m_APPService; 80 | 81 | try { 82 | // create an AALBlock for DSM, size is always 4MB 83 | AALBlock_ptr block(new AALBlock((AALEnv*)env, DSM_SIZE, DSM_SIZE)); 84 | dsm_block = block; 85 | 86 | ((AALEnv*)env)->dsm = block->getWorkspace(); 87 | } 88 | catch (std::exception &e) { 89 | throw e; 90 | } 91 | } 92 | 93 | // 94 | void AALPlatform::serviceAllocated( 95 | IBase *pServiceBase, 96 | TransactionID const &rTranID) 97 | { 98 | m_pAALService = pServiceBase; 99 | if (!m_pAALService) { 100 | m_Status = false; 101 | printf("no m_pAALService allocated\n"); 102 | return; 103 | } 104 | // Documentation says CCIAFU Service publishes ICCIAFU as subclass interface 105 | m_APPService = subclass_ptr(pServiceBase); 106 | 107 | if(!m_APPService) { 108 | m_Status = false; 109 | printf("no m_APPService allocated\n"); 110 | return; 111 | } 112 | m_Sem.Post(1); 113 | } 114 | 115 | void AALPlatform::serviceAllocateFailed(const IEvent &rEvent) 116 | { 117 | IExceptionTransactionEvent * pExEvent = 118 | dynamic_ptr(iidExTranEvent, rEvent); 119 | 120 | ERR("Failed to allocate a Service"); 121 | ERR(pExEvent->Description()); 122 | 123 | m_Status = false; 124 | m_Sem.Post(1); 125 | } 126 | 127 | void AALPlatform::serviceFreed(TransactionID const &rTranID) 128 | { 129 | // Unblock Main() 130 | m_Sem.Post(1); 131 | } 132 | 133 | void AALPlatform::serviceEvent(const IEvent &rEvent) 134 | { 135 | ; 136 | } 137 | // 138 | 139 | } // namespace blaze 140 | -------------------------------------------------------------------------------- /platforms/intel_aal/AALPlatform.h: -------------------------------------------------------------------------------- 1 | #ifndef AAL_PLATFORM_H 2 | #define AAL_PLATFORM_H 3 | 4 | #include 5 | #include 6 | #include 7 | #include 8 | 9 | #include 10 | #include 11 | #include 12 | #include 13 | 14 | #include "proto/acc_conf.pb.h" 15 | #include "Platform.h" 16 | #include "RuntimeClient.h" 17 | #include "AALEnv.h" 18 | #include "AALBlock.h" 19 | 20 | #define DSM_SIZE MB(4) 21 | 22 | namespace blaze { 23 | 24 | class AALPlatform : public blaze::Platform, 25 | public CAASBase, 26 | public IServiceClient, 27 | public ICCIClient 28 | { 29 | public: 30 | 31 | AALPlatform(); 32 | 33 | ~AALPlatform() { 34 | (dynamic_ptr(iidService, m_pAALService))->Release(TransactionID()); 35 | m_Sem.Destroy(); 36 | delete env; 37 | } 38 | 39 | virtual void setupAcc(AccWorker &conf); 40 | 41 | virtual DataBlock_ptr createBlock() { 42 | DataBlock_ptr block( 43 | new AALBlock(static_cast(env))); 44 | return block; 45 | } 46 | 47 | virtual DataBlock_ptr createBlock(size_t length, size_t size) { 48 | DataBlock_ptr block( 49 | new AALBlock(static_cast(env), length, size)); 50 | return block; 51 | } 52 | 53 | // 54 | void serviceAllocated(IBase *pServiceBase, 55 | TransactionID const &rTranID); 56 | 57 | void serviceAllocateFailed(const IEvent &rEvent); 58 | 59 | void serviceFreed(TransactionID const &rTranID); 60 | 61 | void serviceEvent(const IEvent &rEvent); 62 | // 63 | 64 | // 65 | virtual void OnWorkspaceAllocated(TransactionID const &TranID, 66 | btVirtAddr WkspcVirt, 67 | btPhysAddr WkspcPhys, 68 | btWSSize WkspcSize) { 69 | 70 | printf("I was called\n"); 71 | } 72 | 73 | virtual void OnWorkspaceAllocateFailed(const IEvent &Event) {;} 74 | 75 | virtual void OnWorkspaceFreed(TransactionID const &TranID) {;} 76 | 77 | virtual void OnWorkspaceFreeFailed(const IEvent &Event) {;} 78 | // 79 | 80 | private: 81 | 82 | RuntimeClient *m_runtimeClient; 83 | IBase *m_pAALService; // The generic AAL Service interface for the AFU. 84 | ICCIAFU *m_APPService; 85 | 86 | CSemaphore m_Sem; // For synchronizing with the AAL runtime. 87 | btBool m_Status; 88 | 89 | AALBlock_ptr dsm_block; 90 | }; 91 | 92 | extern "C" Platform* create() { 93 | return new AALPlatform(); 94 | } 95 | 96 | extern "C" void destroy(Platform* p) { 97 | delete p; 98 | } 99 | } // namespace blaze 100 | 101 | #endif 102 | -------------------------------------------------------------------------------- /platforms/intel_aal/Makefile: -------------------------------------------------------------------------------- 1 | include ../../Makefile.config 2 | MANAGER_DIR=../../manager 3 | 4 | CPPFLAGS ?= 5 | CXX ?= g++ 6 | LDFLAGS ?= 7 | 8 | ifneq (,$(ndebug)) 9 | else 10 | CPPFLAGS += -DENABLE_DEBUG=1 11 | endif 12 | ifneq (,$(nassert)) 13 | else 14 | CPPFLAGS += -DENABLE_ASSERT=1 15 | endif 16 | 17 | CPPFLAGS += -fPIC -std=c++0x -m64 -g \ 18 | -I$(AAL_DIR)/include \ 19 | -I$(MANAGER_DIR)/include \ 20 | -I$(MANAGER_DIR)/src \ 21 | -I$(BOOST_DIR)/include \ 22 | -I$(PROTOBUF_DIR)/include 23 | 24 | LDFLAGS += -L$(AAL_DIR)/lib -Wl,-rpath-link \ 25 | -Wl,$(AAL_DIR)/lib -Wl,-rpath \ 26 | -Wl,$(AAL_DIR)/lib \ 27 | -L$(AAL_DIR)/lib64 -Wl,-rpath-link \ 28 | -Wl,$(AAL_DIR)/lib64 -Wl,-rpath \ 29 | -Wl,$(AAL_DIR)/lib64 30 | 31 | DEPS= AALPlatform.o \ 32 | AALBlock.o \ 33 | RuntimeClient.o 34 | 35 | all: aal.so 36 | 37 | aal.so: $(DEPS) 38 | $(CXX) -g -shared -o $@ $(DEPS) $(LDFLAGS) -lOSAL -lAAS -lxlrt 39 | 40 | %.o: %.cpp *.h Makefile 41 | $(CXX) $(CPPFLAGS) -D__AAL_USER__=1 -c -o $@ $< 42 | 43 | clean: 44 | $(RM) aal.so *.o 45 | 46 | .PHONY:all clean 47 | -------------------------------------------------------------------------------- /platforms/intel_aal/RuntimeClient.cpp: -------------------------------------------------------------------------------- 1 | #include "RuntimeClient.h" 2 | 3 | RuntimeClient::RuntimeClient() : 4 | m_Runtime(), // Instantiate the AAL Runtime 5 | m_pRuntime(NULL), 6 | m_isOK(false) 7 | { 8 | NamedValueSet configArgs; 9 | NamedValueSet configRecord; 10 | 11 | // Publish our interface 12 | SetSubClassInterface(iidRuntimeClient, dynamic_cast(this)); 13 | 14 | m_Sem.Create(0, 1); 15 | 16 | // Using Hardware Services requires the Remote Resource Manager Broker Service 17 | // Note that this could also be accomplished by setting the environment variable 18 | // XLRUNTIME_CONFIG_BROKER_SERVICE to librrmbroker 19 | #if defined( HWAFU ) 20 | configRecord.Add(XLRUNTIME_CONFIG_BROKER_SERVICE, "librrmbroker"); 21 | configArgs.Add(XLRUNTIME_CONFIG_RECORD,configRecord); 22 | #endif 23 | 24 | if(!m_Runtime.start(this, configArgs)){ 25 | m_isOK = false; 26 | return; 27 | } 28 | m_Sem.Wait(); 29 | } 30 | 31 | RuntimeClient::~RuntimeClient() 32 | { 33 | m_Sem.Destroy(); 34 | } 35 | 36 | btBool RuntimeClient::isOK() 37 | { 38 | return m_isOK; 39 | } 40 | 41 | 42 | void RuntimeClient::runtimeStarted(IRuntime *pRuntime, 43 | const NamedValueSet &rConfigParms) 44 | { 45 | // Save a copy of our runtime interface instance. 46 | m_pRuntime = pRuntime; 47 | m_isOK = true; 48 | m_Sem.Post(1); 49 | } 50 | 51 | void RuntimeClient::end() 52 | { 53 | m_Runtime.stop(); 54 | m_Sem.Wait(); 55 | } 56 | 57 | void RuntimeClient::runtimeStopped(IRuntime *pRuntime) 58 | { 59 | MSG("Runtime stopped"); 60 | m_isOK = false; 61 | m_Sem.Post(1); 62 | } 63 | 64 | void RuntimeClient::runtimeStartFailed(const IEvent &rEvent) 65 | { 66 | IExceptionTransactionEvent * pExEvent = dynamic_ptr(iidExTranEvent, rEvent); 67 | ERR("Runtime start failed"); 68 | ERR(pExEvent->Description()); 69 | } 70 | 71 | void RuntimeClient::runtimeAllocateServiceFailed( IEvent const &rEvent) 72 | { 73 | IExceptionTransactionEvent * pExEvent = dynamic_ptr(iidExTranEvent, rEvent); 74 | ERR("Runtime AllocateService failed"); 75 | ERR(pExEvent->Description()); 76 | 77 | } 78 | 79 | void RuntimeClient::runtimeAllocateServiceSucceeded(IBase *pClient, 80 | TransactionID const &rTranID) 81 | { 82 | MSG("Runtime Allocate Service Succeeded"); 83 | } 84 | 85 | void RuntimeClient::runtimeEvent(const IEvent &rEvent) 86 | { 87 | MSG("Generic message handler (runtime)"); 88 | } 89 | 90 | IRuntime * RuntimeClient::getRuntime() 91 | { 92 | return m_pRuntime; 93 | } 94 | 95 | 96 | -------------------------------------------------------------------------------- /platforms/intel_aal/RuntimeClient.h: -------------------------------------------------------------------------------- 1 | #ifndef RUNTIME_CLIENT_H 2 | #define RUNTIME_CLIENT_H 3 | 4 | #include 5 | #include 6 | #include // Logger 7 | #include 8 | #include 9 | 10 | // Convenience macros for printing messages and errors. 11 | #ifndef MSG 12 | # define MSG(x) std::cout << __AAL_SHORT_FILE__ << ':' << __LINE__ << ':' << __AAL_FUNC__ << "() : " << x << std::endl 13 | #endif // MSG 14 | #ifndef ERR 15 | # define ERR(x) std::cerr << __AAL_SHORT_FILE__ << ':' << __LINE__ << ':' << __AAL_FUNC__ << "() **Error : " << x << std::endl 16 | #endif // ERR 17 | 18 | 19 | using namespace AAL; 20 | 21 | /// @brief Define our Runtime client class so that we can receive the runtime started/stopped notifications. 22 | /// 23 | /// We implement a Service client within, to handle AAL Service allocation/free. 24 | /// We also implement a Semaphore for synchronization with the AAL runtime. 25 | class RuntimeClient : public CAASBase, 26 | public IRuntimeClient 27 | { 28 | public: 29 | RuntimeClient(); 30 | ~RuntimeClient(); 31 | 32 | void end(); 33 | 34 | IRuntime* getRuntime(); 35 | 36 | btBool isOK(); 37 | 38 | // 39 | void runtimeStarted(IRuntime *pRuntime, 40 | const NamedValueSet &rConfigParms); 41 | 42 | void runtimeStopped(IRuntime *pRuntime); 43 | 44 | void runtimeStartFailed(const IEvent &rEvent); 45 | 46 | void runtimeAllocateServiceFailed( IEvent const &rEvent); 47 | 48 | void runtimeAllocateServiceSucceeded(IBase *pClient, 49 | TransactionID const &rTranID); 50 | 51 | void runtimeEvent(const IEvent &rEvent); 52 | 53 | 54 | // 55 | 56 | 57 | protected: 58 | IRuntime *m_pRuntime; // Pointer to AAL runtime instance. 59 | Runtime m_Runtime; // AAL Runtime 60 | btBool m_isOK; // Status 61 | CSemaphore m_Sem; // For synchronizing with the AAL runtime. 62 | }; 63 | 64 | #endif 65 | -------------------------------------------------------------------------------- /platforms/nv_opencl/.gitignore: -------------------------------------------------------------------------------- 1 | *.o 2 | *.so 3 | -------------------------------------------------------------------------------- /platforms/nv_opencl/Makefile: -------------------------------------------------------------------------------- 1 | include ../../Makefile.config 2 | 3 | # check all variables 4 | ifeq ($(BOOST_DIR),) 5 | $(error BOOST_DIR not set properly in Makefile.config) 6 | endif 7 | ifeq ($(PROTOBUF_DIR),) 8 | $(error PROTOBUF_DIR not set properly in Makefile.config) 9 | endif 10 | ifeq ($(CUDA_DIR),) 11 | $(error CUDA_DIR not set properly in Makefile.config) 12 | endif 13 | 14 | PP=g++ 15 | CC=gcc 16 | 17 | MANAGER_DIR=../../manager 18 | 19 | CFLAGS := -c -fPIC -std=c++0x 20 | 21 | ifeq ($(NDEBUG),) 22 | CFLAGS := $(CFLAGS) -g 23 | else 24 | CFLAGS := $(CFLAGS) -O2 -DNDEBUG 25 | endif 26 | 27 | COMPILE := $(CFLAGS) -I./include \ 28 | -I$(MANAGER_DIR)/include \ 29 | -I$(CUDA_DIR)/include \ 30 | -I$(BOOST_DIR)/include \ 31 | -I$(PROTOBUF_DIR)/include \ 32 | -I$(GLOG_DIR)/include \ 33 | -I$(GFLAGS_DIR)/include 34 | 35 | LINK := -L$(MANAGER_DIR)/lib -lblaze \ 36 | -L$(CUDA_DIR)/lib64 -lOpenCL \ 37 | -lpthread -lm -ldl 38 | 39 | DEPS := src/OpenCLPlatform.o \ 40 | src/OpenCLTaskEnv.o \ 41 | src/OpenCLBlock.o \ 42 | src/OpenCLQueueManager.o 43 | 44 | PKG_DIR := ../../package 45 | 46 | INC_LIST:= ./include/blaze/nv_opencl/OpenCLEnv.h \ 47 | ./include/blaze/nv_opencl/OpenCLCommon.h 48 | 49 | all: nv_opencl.so 50 | 51 | package: 52 | for file in $(INC_LIST); do \ 53 | cp $$file $(PKG_DIR)/include/blaze/nv_opencl; \ 54 | done 55 | cp nv_opencl.so $(PKG_DIR)/nam/lib 56 | 57 | release: 58 | $(MAKE) NDEBUG=1 59 | 60 | nv_opencl.so: $(DEPS) 61 | $(PP) -shared -o $@ $(DEPS) $(LINK) 62 | 63 | src/%.o: src/%.cpp include/blaze/nv_opencl/*.h 64 | $(PP) $(COMPILE) $< -o $@ 65 | 66 | clean: 67 | rm -rf src/*.o 68 | rm -rf nv_opencl.so 69 | -------------------------------------------------------------------------------- /platforms/nv_opencl/include/blaze/nv_opencl/OpenCLBlock.h: -------------------------------------------------------------------------------- 1 | #ifndef OPENCLBLOCK_H 2 | #define OPENCLBLOCK_H 3 | 4 | #include 5 | #include 6 | #include 7 | #include 8 | 9 | #include 10 | #include 11 | 12 | #include "blaze/Block.h" 13 | #include "OpenCLCommon.h" 14 | #include "OpenCLEnv.h" 15 | 16 | namespace blaze { 17 | 18 | class OpenCLBlock : public DataBlock 19 | { 20 | friend class OpenCLQueueManager; 21 | 22 | public: 23 | // create a single output elements 24 | OpenCLBlock( 25 | std::vector &_env_list, 26 | int _num_items, 27 | int _item_length, 28 | int _item_size, 29 | int _align_width = 0, 30 | int _flag = BLAZE_INPUT_BLOCK); 31 | 32 | OpenCLBlock(const OpenCLBlock& block); 33 | 34 | ~OpenCLBlock(); 35 | 36 | virtual void alloc(); 37 | 38 | // read/write data from/to shared memory 39 | virtual void readFromMem(std::string path); 40 | virtual void writeToMem(std::string path); 41 | 42 | // copy data from an array 43 | virtual void writeData(void* src, size_t _size); 44 | virtual void writeData(void* src, size_t _size, size_t offset); 45 | 46 | // write data to an array 47 | virtual void readData(void* dst, size_t size); 48 | 49 | // sample the items in the block by a mask 50 | virtual DataBlock_ptr sample(char* mask); 51 | 52 | virtual char* getData(); 53 | 54 | // relocate the block to another device memory 55 | void relocate(int loc); 56 | 57 | int getDeviceId(); 58 | 59 | private: 60 | cl_mem* data; 61 | 62 | // index of device where the block is allocated 63 | int location; 64 | 65 | int num_devices; 66 | 67 | std::vector &env_list; 68 | }; 69 | } 70 | 71 | #endif 72 | -------------------------------------------------------------------------------- /platforms/nv_opencl/include/blaze/nv_opencl/OpenCLCommon.h: -------------------------------------------------------------------------------- 1 | #ifndef OPENCL_COMMON_H 2 | #define OPENCL_COMMON_H 3 | 4 | #include "blaze/Common.h" 5 | 6 | namespace blaze { 7 | class OpenCLPlatform; 8 | class OpenCLBlock; 9 | class OpenCLEnv; 10 | class OpenCLTaskEnv; 11 | class OpenCLQueueManager; 12 | } 13 | 14 | #endif 15 | -------------------------------------------------------------------------------- /platforms/nv_opencl/include/blaze/nv_opencl/OpenCLEnv.h: -------------------------------------------------------------------------------- 1 | #ifndef OPENCLENV_H 2 | #define OPENCLENV_H 3 | 4 | #include 5 | #include 6 | #include 7 | #include 8 | 9 | #include 10 | #include 11 | #include 12 | 13 | #include "blaze/TaskEnv.h" 14 | #include "OpenCLCommon.h" 15 | 16 | namespace blaze { 17 | 18 | class OpenCLEnv 19 | : public boost::basic_lockable_adapter 20 | { 21 | public: 22 | OpenCLEnv( 23 | int _id, 24 | cl_context _context, 25 | cl_command_queue _queue, 26 | cl_device_id _device_id): 27 | id(_id), 28 | context(_context), 29 | cmd_queue(_queue), 30 | device_id(_device_id) 31 | {;} 32 | 33 | int getDevice() { return id; } 34 | cl_device_id& getDeviceId() { return device_id; } 35 | cl_context& getContext() { return context; } 36 | cl_command_queue& getCmdQueue() { return cmd_queue; } 37 | 38 | private: 39 | int id; 40 | cl_device_id device_id; 41 | cl_context context; 42 | cl_command_queue cmd_queue; 43 | }; 44 | 45 | class OpenCLTaskEnv : public TaskEnv 46 | { 47 | friend class OpenCLQueueManager; 48 | 49 | public: 50 | OpenCLTaskEnv( 51 | std::vector& _env_list, 52 | std::vector& _program_list): 53 | env_list(_env_list), 54 | program_list(_program_list), 55 | location(-1) 56 | { 57 | num_devices = _env_list.size(); 58 | } 59 | 60 | cl_context getContext() { 61 | if (location < 0) { 62 | return 0; 63 | } else { 64 | return env_list[location]->getContext(); 65 | } 66 | } 67 | cl_command_queue getCmdQueue() { 68 | if (location < 0) { 69 | return 0; 70 | } else { 71 | return env_list[location]->getCmdQueue(); 72 | } 73 | } 74 | cl_program getProgram() { 75 | if (location < 0) { 76 | return 0; 77 | } else { 78 | return program_list[location]; 79 | } 80 | } 81 | virtual DataBlock_ptr createBlock( 82 | int num_items, 83 | int item_length, 84 | int item_size, 85 | int align_width = 0, 86 | int flag = BLAZE_OUTPUT_BLOCK); 87 | 88 | virtual DataBlock_ptr createBlock(const OpenCLBlock& block); 89 | 90 | void relocate(int loc); 91 | 92 | private: 93 | std::vector &env_list; 94 | std::vector &program_list; 95 | 96 | // index of device where the block is allocated 97 | int location; 98 | 99 | int num_devices; 100 | 101 | }; 102 | } 103 | 104 | #endif 105 | -------------------------------------------------------------------------------- /platforms/nv_opencl/include/blaze/nv_opencl/OpenCLPlatform.h: -------------------------------------------------------------------------------- 1 | #ifndef OPENCL_PLATFORM_H 2 | #define OPENCL_PLATFORM_H 3 | 4 | #include 5 | #include 6 | #include 7 | #include 8 | 9 | #include 10 | 11 | #include "blaze/Platform.h" 12 | #include "OpenCLCommon.h" 13 | 14 | namespace blaze { 15 | 16 | class OpenCLPlatform : public Platform { 17 | 18 | public: 19 | 20 | OpenCLPlatform(std::map &conf_table); 21 | 22 | ~OpenCLPlatform(); 23 | 24 | virtual DataBlock_ptr createBlock( 25 | int num_items, 26 | int item_length, 27 | int item_size, 28 | int align_width = 0, 29 | int flag = BLAZE_INPUT_BLOCK); 30 | 31 | virtual DataBlock_ptr createBlock( 32 | const OpenCLBlock& block); 33 | 34 | int getNumDevices(); 35 | 36 | virtual TaskEnv_ptr getEnv(std::string id); 37 | 38 | OpenCLEnv* getEnv(int device_id); 39 | 40 | void addQueue(AccWorker &conf); 41 | 42 | private: 43 | int load_file(const char* filename, char** result); 44 | 45 | uint32_t num_devices; 46 | 47 | std::vector env_list; 48 | 49 | std::map > program_list; 50 | 51 | std::vector block_manager_list; 52 | }; 53 | 54 | extern "C" Platform* create( 55 | std::map &config_table); 56 | 57 | extern "C" void destroy(Platform* p); 58 | 59 | } // namespace blaze 60 | 61 | #endif 62 | -------------------------------------------------------------------------------- /platforms/nv_opencl/include/blaze/nv_opencl/OpenCLQueueManager.h: -------------------------------------------------------------------------------- 1 | #ifndef OPENCL_QUEUE_MANAGER_H 2 | #define OPENCL_QUEUE_MANAGER_H 3 | 4 | #include "blaze/QueueManager.h" 5 | #include "blaze/TaskQueue.h" 6 | #include "OpenCLCommon.h" 7 | 8 | namespace blaze { 9 | 10 | class OpenCLQueueManager : public QueueManager { 11 | public: 12 | 13 | OpenCLQueueManager(Platform* _platform); 14 | 15 | // start dispatch and executors for all GPU devices 16 | void start(std::string id); 17 | 18 | private: 19 | OpenCLPlatform* ocl_platform; 20 | 21 | // thread body of dispatching tasks from 22 | // TaskQueue to PlatformQueue 23 | void do_dispatch(); 24 | 25 | // thread body of PlatformQueue 26 | void do_execute(int device_id); 27 | 28 | // Platform Queues 29 | std::vector platform_queues; 30 | }; 31 | } // namespace blaze 32 | 33 | #endif 34 | -------------------------------------------------------------------------------- /platforms/nv_opencl/src/OpenCLTaskEnv.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include "blaze/nv_opencl/OpenCLBlock.h" 3 | #include "blaze/nv_opencl/OpenCLEnv.h" 4 | 5 | namespace blaze { 6 | 7 | DataBlock_ptr OpenCLTaskEnv::createBlock( 8 | int num_items, int item_length, 9 | int item_size, int align_width, 10 | int flag) 11 | { 12 | OpenCLBlock* new_block = new OpenCLBlock(env_list, 13 | num_items, item_length, item_size, align_width, flag); 14 | 15 | new_block->relocate(location); 16 | 17 | DataBlock_ptr block(new_block); 18 | 19 | return block; 20 | } 21 | 22 | DataBlock_ptr OpenCLTaskEnv::createBlock( 23 | const OpenCLBlock& block) 24 | { 25 | DataBlock_ptr bp( 26 | new OpenCLBlock(block)); 27 | return bp; 28 | } 29 | 30 | 31 | void OpenCLTaskEnv::relocate(int loc) { 32 | location = loc; 33 | } 34 | 35 | } 36 | -------------------------------------------------------------------------------- /setup.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | DIR=$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd ) 4 | source $DIR/Makefile.config 5 | 6 | export BLAZE_HOME=$DIR 7 | export SPARK_HOME=$DIR/spark-1.5.1 8 | export LD_LIBRARY_PATH=$BOOST_DIR/lib:$LD_LIBRARY_PATH 9 | export LD_LIBRARY_PATH=$PROTOBUF_DIR/lib:$LD_LIBRARY_PATH 10 | export LD_LIBRARY_PATH=$GLOG_DIR/lib:$LD_LIBRARY_PATH 11 | export LD_LIBRARY_PATH=$HADOOP_DIR/lib/native:$LD_LIBRARY_PATH 12 | export LD_LIBRARY_PATH=$JAVA_HOME/jre/lib/amd64/server:$LD_LIBRARY_PATH 13 | export LD_LIBRARY_PATH=$MKL_DIR/lib/intel64:$LD_LIBRARY_PATH 14 | export LD_LIBRARY_PATH=$BLAZE_HOME/manager/lib:$LD_LIBRARY_PATH 15 | export PATH=$PROTOBUF_DIR/bin:$PATH 16 | --------------------------------------------------------------------------------