summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--Jenkinsfile87
-rw-r--r--cuobjdump_to_ptxplus/Makefile8
-rw-r--r--cuobjdump_to_ptxplus/ptx.l471
-rw-r--r--cuobjdump_to_ptxplus/ptx.y629
-rw-r--r--diff.diff173
-rw-r--r--groovy-html.nightly.success.template74
-rw-r--r--groovy-html.success.template77
-rw-r--r--libcuda/Makefile4
-rw-r--r--libcuda/cuda_api_object.h213
-rw-r--r--libcuda/cuda_runtime_api.cc2262
-rw-r--r--libcuda/cuobjdump.h80
-rw-r--r--libcuda/cuobjdump.l56
-rw-r--r--libcuda/cuobjdump.y77
-rw-r--r--libcuda/gpgpu_context.h71
-rw-r--r--libopencl/opencl_runtime_api.cc35
-rw-r--r--nightly.jenkinsfile58
-rw-r--r--setup_environment14
-rw-r--r--src/Makefile2
-rw-r--r--src/abstract_hardware_model.cc79
-rw-r--r--src/abstract_hardware_model.h117
-rw-r--r--src/cuda-sim/Makefile8
-rw-r--r--src/cuda-sim/cuda-math.h16
-rw-r--r--src/cuda-sim/cuda-sim.cc218
-rw-r--r--src/cuda-sim/cuda-sim.h111
-rw-r--r--src/cuda-sim/cuda_device_runtime.cc59
-rw-r--r--src/cuda-sim/cuda_device_runtime.h69
-rw-r--r--src/cuda-sim/instructions.cc85
-rw-r--r--src/cuda-sim/memory.cc3
-rw-r--r--src/cuda-sim/ptx-stats.cc37
-rw-r--r--src/cuda-sim/ptx-stats.h38
-rw-r--r--src/cuda-sim/ptx.l331
-rw-r--r--src/cuda-sim/ptx.y498
-rw-r--r--src/cuda-sim/ptx_ir.cc54
-rw-r--r--src/cuda-sim/ptx_ir.h92
-rw-r--r--src/cuda-sim/ptx_loader.cc99
-rw-r--r--src/cuda-sim/ptx_loader.h28
-rw-r--r--src/cuda-sim/ptx_parser.cc286
-rw-r--r--src/cuda-sim/ptx_parser.h216
-rw-r--r--src/cuda-sim/ptx_sim.cc36
-rw-r--r--src/cuda-sim/ptx_sim.h5
-rw-r--r--src/cuda-sim/ptxinfo.l45
-rw-r--r--src/cuda-sim/ptxinfo.y18
-rw-r--r--src/debug.cc23
-rw-r--r--src/debug.h3
-rw-r--r--src/gpgpu-sim/Makefile2
-rw-r--r--src/gpgpu-sim/dram.cc24
-rw-r--r--src/gpgpu-sim/dram.h11
-rw-r--r--src/gpgpu-sim/dram_sched.cc14
-rw-r--r--src/gpgpu-sim/gpu-cache.cc21
-rw-r--r--src/gpgpu-sim/gpu-cache.h21
-rw-r--r--src/gpgpu-sim/gpu-sim.cc89
-rw-r--r--src/gpgpu-sim/gpu-sim.h71
-rw-r--r--src/gpgpu-sim/l2cache.cc81
-rw-r--r--src/gpgpu-sim/l2cache.h21
-rw-r--r--src/gpgpu-sim/l2cache_trace.h4
-rw-r--r--src/gpgpu-sim/mem_fetch.cc9
-rw-r--r--src/gpgpu-sim/mem_fetch.h6
-rw-r--r--src/gpgpu-sim/mem_latency_stat.cc12
-rw-r--r--src/gpgpu-sim/mem_latency_stat.h11
-rw-r--r--src/gpgpu-sim/power_interface.cc2
-rw-r--r--src/gpgpu-sim/power_interface.h2
-rw-r--r--src/gpgpu-sim/power_stat.cc6
-rw-r--r--src/gpgpu-sim/power_stat.h8
-rw-r--r--src/gpgpu-sim/scoreboard.cc4
-rw-r--r--src/gpgpu-sim/scoreboard.h4
-rw-r--r--src/gpgpu-sim/shader.cc120
-rw-r--r--src/gpgpu-sim/shader.h49
-rw-r--r--src/gpgpu-sim/shader_trace.h4
-rw-r--r--src/gpgpu-sim/stat-tool.cc33
-rw-r--r--src/gpgpu-sim/stat-tool.h12
-rw-r--r--src/gpgpusim_entrypoint.cc178
-rw-r--r--src/gpgpusim_entrypoint.h51
-rw-r--r--src/intersim2/Makefile1
-rw-r--r--src/option_parser.cc3
-rw-r--r--src/stream_manager.cc7
-rw-r--r--src/trace.h14
-rw-r--r--version_detection.mk5
77 files changed, 4853 insertions, 3012 deletions
diff --git a/Jenkinsfile b/Jenkinsfile
index 4bdbddf..a345bc0 100644
--- a/Jenkinsfile
+++ b/Jenkinsfile
@@ -14,8 +14,8 @@ pipeline {
sh 'source /home/tgrogers-raid/a/common/gpgpu-sim-setup/4.2_env_setup.sh &&\
source `pwd`/setup_environment &&\
make -j'
- }, "9.1" : {
- sh 'source /home/tgrogers-raid/a/common/gpgpu-sim-setup/9.1_env_setup.sh &&\
+ }, "10.1" : {
+ sh 'source /home/tgrogers-raid/a/common/gpgpu-sim-setup/10.1_env_setup.sh &&\
source `pwd`/setup_environment &&\
make -j'
}
@@ -24,7 +24,7 @@ pipeline {
stage('simulations-build'){
steps{
sh 'rm -rf gpgpu-sim_simulations'
- sh 'git clone [email protected]:gpgpu-sim/gpgpu-sim_simulations.git && \
+ sh 'git clone [email protected]:purdue-aalp/gpgpu-sim_simulations.git && \
cd gpgpu-sim_simulations && \
git pull && \
ln -s /home/tgrogers-raid/a/common/data_dirs benchmarks/'
@@ -34,7 +34,7 @@ pipeline {
source ./benchmarks/src/setup_environment && \
make -j -C ./benchmarks/src rodinia_2.0-ft sdk-4.2 && \
make -C ./benchmarks/src data'
- sh 'source /home/tgrogers-raid/a/common/gpgpu-sim-setup/9.1_env_setup.sh &&\
+ sh 'source /home/tgrogers-raid/a/common/gpgpu-sim-setup/10.1_env_setup.sh &&\
source `pwd`/setup_environment &&\
cd gpgpu-sim_simulations && \
source ./benchmarks/src/setup_environment && \
@@ -47,71 +47,58 @@ pipeline {
parallel "4.2-rodinia": {
sh 'source /home/tgrogers-raid/a/common/gpgpu-sim-setup/4.2_env_setup.sh &&\
source `pwd`/setup_environment &&\
- ./gpgpu-sim_simulations/util/job_launching/run_simulations.py -B rodinia_2.0-ft -C GTX480,GTX480-PTXPLUS -N regress-$$ && \
- PLOTDIR="jenkins/${JOB_NAME}/${BUILD_NUMBER}/4.2-rodinia" && ssh [email protected] mkdir -p /home/dynamo/a/tgrogers/website/gpgpu-sim-plots/$PLOTDIR && \
- ./gpgpu-sim_simulations/util/job_launching/monitor_func_test.py -v -N regress-$$ -s stats-per-app-4.2.csv && \
- ./gpgpu-sim_simulations/util/plotting/plot-get-stats.py -c stats-per-app-4.2.csv -p [email protected]:~/website/gpgpu-sim-plots/$PLOTDIR -w https://engineering.purdue.edu/tgrogers/gpgpu-sim-plots/$PLOTDIR -n $PLOTDIR '
- }, "9.1-functest": {
- sh 'source /home/tgrogers-raid/a/common/gpgpu-sim-setup/9.1_env_setup.sh &&\
+ export PTXAS_CUDA_INSTALL_PATH=/home/tgrogers-raid/a/common/cuda-10.1 &&\
+ ./gpgpu-sim_simulations/util/job_launching/run_simulations.py -B rodinia_2.0-ft -C TITANV-PTXPLUS -N regress-$$ && \
+ PLOTDIR="jenkins/${JOB_NAME}/${BUILD_NUMBER}/4.2" && ssh [email protected] mkdir -p /home/dynamo/a/tgrogers/website/gpgpu-sim-plots/$PLOTDIR && \
+ ./gpgpu-sim_simulations/util/job_launching/monitor_func_test.py -v -N regress-$$ -s stats-per-app-4.2.csv'
+ }, "10.1-functest": {
+ sh 'source /home/tgrogers-raid/a/common/gpgpu-sim-setup/10.1_env_setup.sh &&\
source `pwd`/setup_environment &&\
./gpgpu-sim_simulations/util/job_launching/run_simulations.py -B rodinia_2.0-ft,sdk-4.2 -C TITANV -N regress-$$ && \
- PLOTDIR="jenkins/${JOB_NAME}/${BUILD_NUMBER}/9.1-rodinia" && ssh [email protected] mkdir -p /home/dynamo/a/tgrogers/website/gpgpu-sim-plots/$PLOTDIR && \
- ./gpgpu-sim_simulations/util/job_launching/monitor_func_test.py -v -s stats-per-app-9.1.csv -N regress-$$ && \
- ./gpgpu-sim_simulations/util/plotting/plot-get-stats.py -c stats-per-app-9.1.csv -p [email protected]:~/website/gpgpu-sim-plots/$PLOTDIR -w https://engineering.purdue.edu/tgrogers/gpgpu-sim-plots/$PLOTDIR -n $PLOTDIR'
+ PLOTDIR="jenkins/${JOB_NAME}/${BUILD_NUMBER}/10.1" && ssh [email protected] mkdir -p /home/dynamo/a/tgrogers/website/gpgpu-sim-plots/$PLOTDIR && \
+ ./gpgpu-sim_simulations/util/job_launching/monitor_func_test.py -v -s stats-per-app-10.1.csv -N regress-$$'
}
}
}
- stage('4.2-correlate'){
+ stage('correlate-delta-and-archive') {
steps {
- sh 'source /home/tgrogers-raid/a/common/gpgpu-sim-setup/4.2_env_setup.sh &&\
- source `pwd`/setup_environment &&\
- PLOTDIR="jenkins/${JOB_NAME}" &&\
- ./gpgpu-sim_simulations/util/job_launching/get_stats.py -R -K -k -B rodinia_2.0-ft -C GTX480,GTX480-PTXPLUS > stats-per-kernel-4.2.csv &&\
- ./gpgpu-sim_simulations/util/plotting/correlate_and_publish.sh stats-per-kernel-4.2.csv $PLOTDIR ${BUILD_NUMBER}'
- }
- }
- stage('9.1-correlate'){
- steps {
- sh 'source /home/tgrogers-raid/a/common/gpgpu-sim-setup/9.1_env_setup.sh &&\
- source `pwd`/setup_environment &&\
- PLOTDIR="jenkins/${JOB_NAME}" &&\
- ./gpgpu-sim_simulations/util/job_launching/get_stats.py -R -K -k -B rodinia_2.0-ft,sdk-4.2 -C TITANV > stats-per-kernel-9.1.csv &&\
- ./gpgpu-sim_simulations/util/plotting/correlate_and_publish.sh stats-per-kernel-9.1.csv $PLOTDIR ${BUILD_NUMBER}'
- }
- }
- stage('archive-and-delta') {
- steps {
- sh 'rm -rf gpgpu-sim-results-repo'
+ sh './gpgpu-sim_simulations/run_hw/get_hw_data.sh'
+ sh 'rm -rf ./gpgpu-sim_simulations/util/plotting/correl-html && rm -rf gpgpu-sim-results-repo && rm -rf ./gpgpu-sim_simulations/util/plotting/htmls'
sh 'git clone [email protected]:purdue-aalp/gpgpu-sim-results-repo.git'
sh 'source /home/tgrogers-raid/a/common/gpgpu-sim-setup/4.2_env_setup.sh &&\
- ./gpgpu-sim_simulations/util/job_launching/get_stats.py -R -K -k -B rodinia_2.0-ft -C GTX480-PTXPLUS > stats-per-kernel-4.2-ptxplus.csv &&\
- ./gpgpu-sim_simulations/util/job_launching/get_stats.py -R -K -k -B rodinia_2.0-ft -C GTX480 > stats-per-kernel-4.2-ptx.csv'
- sh 'source /home/tgrogers-raid/a/common/gpgpu-sim-setup/9.1_env_setup.sh &&\
- ./gpgpu-sim_simulations/util/job_launching/get_stats.py -R -K -k -B rodinia_2.0-ft,sdk-4.2 -C TITANV > stats-per-kernel-9.1-titanx.csv'
- sh './gpgpu-sim_simulations/util/plotting/merge-stats.py -c ./gpgpu-sim-results-repo/jenkins/quick-regress/AALP/gpgpu-sim_distribution/dev-purdue-integration/stats-per-app-4.2.csv,./stats-per-app-4.2.csv -R > per-app-merge-4.2.csv'
- sh './gpgpu-sim_simulations/util/plotting/merge-stats.py -c ./gpgpu-sim-results-repo/jenkins/quick-regress/AALP/gpgpu-sim_distribution/dev-purdue-integration/stats-per-app-9.1.csv,./stats-per-app-9.1.csv -R > per-app-merge-9.1.csv'
+ ./gpgpu-sim_simulations/util/job_launching/get_stats.py -R -K -k -B rodinia_2.0-ft -C TITANV-PTXPLUS -A > stats-per-kernel-4.2-ptxplus.csv'
+ sh 'source /home/tgrogers-raid/a/common/gpgpu-sim-setup/10.1_env_setup.sh &&\
+ ./gpgpu-sim_simulations/util/job_launching/get_stats.py -R -K -k -B rodinia_2.0-ft,sdk-4.2 -C TITANV -A > stats-per-kernel-10.1.csv'
+ sh 'if [ ! -d ./gpgpu-sim-results-repo/${JOB_NAME} ]; then mkdir -p ./gpgpu-sim-results-repo/${JOB_NAME}/ ; cp ./gpgpu-sim-results-repo/purdue-aalp/gpgpu-sim_distribution/dev/* ./gpgpu-sim-results-repo/${JOB_NAME}/ ; fi'
+ sh './gpgpu-sim_simulations/util/plotting/merge-stats.py -c ./gpgpu-sim-results-repo/${JOB_NAME}/stats-per-app-4.2.csv,./stats-per-app-4.2.csv -R > per-app-merge-4.2.csv'
+ sh './gpgpu-sim_simulations/util/plotting/merge-stats.py -c ./gpgpu-sim-results-repo/${JOB_NAME}/stats-per-app-10.1.csv,./stats-per-app-10.1.csv -R > per-app-merge-10.1.csv'
sh 'PLOTDIR="jenkins/${JOB_NAME}" &&\
- ./gpgpu-sim_simulations/util/plotting/plot-get-stats.py -c per-app-merge-4.2.csv -p [email protected]:~/website/gpgpu-sim-plots/$PLOTDIR/deltas -w https://engineering.purdue.edu/tgrogers/gpgpu-sim-plots/$PLOTDIR -n $PLOTDIR/deltas &&\
- ./gpgpu-sim_simulations/util/plotting/plot-get-stats.py -c per-app-merge-9.1.csv -p [email protected]:~/website/gpgpu-sim-plots/$PLOTDIR/deltas -w https://engineering.purdue.edu/tgrogers/gpgpu-sim-plots/$PLOTDIR/deltas -n $PLOTDIR/deltas &&\
- ./gpgpu-sim_simulations/util/plotting/merge-stats.py -c ./gpgpu-sim-results-repo/jenkins/quick-regress/AALP/gpgpu-sim_distribution/dev-purdue-integration/stats-per-kernel-4.2-ptx.csv,./stats-per-kernel-4.2-ptx.csv -R > per-kernel-merge-4.2-ptx.csv &&\
- ./gpgpu-sim_simulations/util/plotting/merge-stats.py -c ./gpgpu-sim-results-repo/jenkins/quick-regress/AALP/gpgpu-sim_distribution/dev-purdue-integration/stats-per-kernel-4.2-ptxplus.csv,./stats-per-kernel-4.2-ptxplus.csv -R > per-kernel-merge-4.2-ptxplus.csv &&\
- ./gpgpu-sim_simulations/util/plotting/merge-stats.py -c ./gpgpu-sim-results-repo/jenkins/quick-regress/AALP/gpgpu-sim_distribution/dev-purdue-integration/stats-per-kernel-9.1-titanx.csv,./stats-per-kernel-9.1-titanx.csv -R > per-kernel-merge-9.1-titanx.csv &&\
- ./gpgpu-sim_simulations/util/plotting/correlate_and_publish.sh per-kernel-merge-4.2-ptx.csv $PLOTDIR ${BUILD_NUMBER} &&\
- ./gpgpu-sim_simulations/util/plotting/correlate_and_publish.sh per-kernel-merge-4.2-ptxplus.csv $PLOTDIR ${BUILD_NUMBER} &&\
- ./gpgpu-sim_simulations/util/plotting/correlate_and_publish.sh per-kernel-merge-9.1-titanx.csv $PLOTDIR ${BUILD_NUMBER} &&\
- mkdir -p ./jenkins/quick-regress/${JOB_NAME}/ && cp stats-per-*.csv ./jenkins/quick-regress/${JOB_NAME}/ &&\
+ ./gpgpu-sim_simulations/util/plotting/plot-get-stats.py -c per-app-merge-4.2.csv -P cuda-4.2 &&\
+ ./gpgpu-sim_simulations/util/plotting/plot-get-stats.py -c per-app-merge-10.1.csv -P cuda-10.1 &&\
+ ./gpgpu-sim_simulations/util/plotting/merge-stats.py -c ./gpgpu-sim-results-repo/${JOB_NAME}/stats-per-kernel-4.2-ptxplus.csv,./stats-per-kernel-4.2-ptxplus.csv -R > per-kernel-merge-4.2-ptxplus.csv &&\
+ ./gpgpu-sim_simulations/util/plotting/merge-stats.py -c ./gpgpu-sim-results-repo/${JOB_NAME}/stats-per-kernel-10.1.csv,./stats-per-kernel-10.1.csv -R > per-kernel-merge-10.1.csv &&\
+ ./gpgpu-sim_simulations/util/plotting/plot-correlation.py -c per-kernel-merge-4.2-ptxplus.csv -p cuda-4.2 | grep "Correl=" | tee correl.4.2.txt &&\
+ ./gpgpu-sim_simulations/util/plotting/plot-correlation.py -c per-kernel-merge-10.1.csv -p cuda-10.1 | grep "Correl=" | tee correl.10.1.txt &&\
+ mkdir -p ./gpgpu-sim-results-repo/${JOB_NAME}/ && cp stats-per-*.csv ./gpgpu-sim-results-repo/${JOB_NAME}/ &&\
cd ./gpgpu-sim-results-repo &&\
- git diff --quiet && git diff --staged --quiet || git commit -am "Jenkins automated checkin ${BUILD_NUMBER}" &&\
+ git diff --quiet && git diff --staged --quiet || git commit -am "Jenkins automated checkin ${JOB_NAME} Build:${BUILD_NUMBER}" &&\
git push'
+
+ sh 'PLOTDIR="/home/dynamo/a/tgrogers/website/gpgpu-sim-plots/jenkins/${JOB_NAME}" &&\
+ ssh [email protected] mkdir -p $PLOTDIR/${BUILD_NUMBER} && \
+ scp ./gpgpu-sim_simulations/util/plotting/correl-html/* [email protected]:$PLOTDIR/${BUILD_NUMBER} &&\
+ scp ./gpgpu-sim_simulations/util/plotting/htmls/* [email protected]:$PLOTDIR/${BUILD_NUMBER} &&\
+ ssh [email protected] "cd $PLOTDIR && rm -rf latest && cp -r ${BUILD_NUMBER} latest"'
}
}
}
post {
success {
- emailext body: "See ${BUILD_URL}",
+ emailext body:'''${SCRIPT, template="groovy-html.success.template"}''',
recipientProviders: [[$class: 'CulpritsRecipientProvider'],
[$class: 'RequesterRecipientProvider']],
subject: "[AALP Jenkins] Build #${BUILD_NUMBER} - Success!",
+ attachmentsPattern: 'correl.*.txt',
}
failure {
diff --git a/cuobjdump_to_ptxplus/Makefile b/cuobjdump_to_ptxplus/Makefile
index 242a066..e95136a 100644
--- a/cuobjdump_to_ptxplus/Makefile
+++ b/cuobjdump_to_ptxplus/Makefile
@@ -27,11 +27,11 @@ $(OUTPUT_DIR)/cuobjdump_to_ptxplus: $(OUTPUT_DIR)/cuobjdumpInst.o $(OUTPUT_DIR)/
${LD} ${LDFLAGS} -o $@ $(OUTPUT_DIR)/cuobjdumpInst.o $(OUTPUT_DIR)/cuobjdumpInstList.o $(OUTPUT_DIR)/cuobjdump_to_ptxplus.o $(PTX_PARSER_OBJECTS) $(SASS_PARSER_OBJECTS) $(ELF_PARSER_OBJECTS) $(HEADER_PARSER_OBJECTS)
-$(OUTPUT_DIR)/lex.ptx_.c : ../src/cuda-sim/ptx.l
- ${LEX} ${LEXFLAGS} -o$(OUTPUT_DIR)/lex.ptx_.c ../src/cuda-sim/ptx.l
+$(OUTPUT_DIR)/lex.ptx_.c : ptx.l
+ ${LEX} ${LEXFLAGS} -o$(OUTPUT_DIR)/lex.ptx_.c ptx.l
-$(OUTPUT_DIR)/ptx.tab.c : ../src/cuda-sim/ptx.y
- ${YACC} ${YFLAGS} --name-prefix=ptx_ -v ../src/cuda-sim/ptx.y --file-prefix=$(OUTPUT_DIR)/ptx
+$(OUTPUT_DIR)/ptx.tab.c : ptx.y
+ ${YACC} ${YFLAGS} --name-prefix=ptx_ -v ptx.y --file-prefix=$(OUTPUT_DIR)/ptx
$(OUTPUT_DIR)/ptx.tab.h :$(OUTPUT_DIR)/ptx.tab.c
diff --git a/cuobjdump_to_ptxplus/ptx.l b/cuobjdump_to_ptxplus/ptx.l
new file mode 100644
index 0000000..3232361
--- /dev/null
+++ b/cuobjdump_to_ptxplus/ptx.l
@@ -0,0 +1,471 @@
+/*
+Copyright (c) 2009-2011, Tor M. Aamodt
+The University of British Columbia
+All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are met:
+
+Redistributions of source code must retain the above copyright notice, this
+list of conditions and the following disclaimer.
+Redistributions in binary form must reproduce the above copyright notice, this
+list of conditions and the following disclaimer in the documentation and/or
+other materials provided with the distribution.
+Neither the name of The University of British Columbia nor the names of its
+contributors may be used to endorse or promote products derived from this
+software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
+ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
+FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+*/
+
+%option nounput
+%option noyywrap
+%option yylineno
+%option prefix="ptx_"
+%{
+#include "opcodes.h"
+#include "ptx.tab.h"
+#include <string.h>
+
+#define LINEBUF_SIZE (64*1024)
+char linebuf[LINEBUF_SIZE];
+unsigned col = 0;
+#define TC col+=strlen(ptx_text);
+#define CHECK_UNSIGNED \
+ if( yytext[strlen(yytext)-1]=='U' ) { \
+ printf("GPGPU-Sim: ERROR ** U modifier not implemented\n"); \
+ abort(); \
+ }
+int ptx_error( const char *s );
+%}
+
+%s IN_STRING
+%s IN_COMMENT
+%x IN_FUNC_DECL
+%x NOT_OPCODE
+%%
+
+abs TC; ptx_lval.int_value = ABS_OP; return OPCODE;
+add TC; ptx_lval.int_value = ADD_OP; return OPCODE;
+addp TC; ptx_lval.int_value = ADDP_OP; return OPCODE;
+addc TC; ptx_lval.int_value = ADDC_OP; return OPCODE;
+and TC; ptx_lval.int_value = AND_OP; return OPCODE;
+andn TC; ptx_lval.int_value = ANDN_OP; return OPCODE;
+atom TC; ptx_lval.int_value = ATOM_OP; return OPCODE;
+bar.warp TC; ptx_lval.int_value = NOP_OP; return OPCODE;
+bar TC; ptx_lval.int_value = BAR_OP; return OPCODE;
+bfe TC; ptx_lval.int_value = BFE_OP; return OPCODE;
+bfi TC; ptx_lval.int_value = BFI_OP; return OPCODE;
+bfind TC; ptx_lval.int_value = BFIND_OP; return OPCODE;
+bra TC; ptx_lval.int_value = BRA_OP; return OPCODE;
+brx TC; ptx_lval.int_value = BRX_OP; return OPCODE;
+brev TC; ptx_lval.int_value = BREV_OP; return OPCODE;
+brkpt TC; ptx_lval.int_value = BRKPT_OP; return OPCODE;
+
+wmma TC; ptx_lval.int_value = MMA_OP; return OPCODE;
+wmma\.load TC; ptx_lval.int_value = MMA_LD_OP; return OPCODE;
+wmma\.store TC; ptx_lval.int_value = MMA_ST_OP; return OPCODE;
+
+call TC; BEGIN(NOT_OPCODE); ptx_lval.int_value = CALL_OP; return OPCODE; // blocking opcode token in case the callee has the same name as an opcode
+callp TC; BEGIN(NOT_OPCODE); ptx_lval.int_value = CALLP_OP; return OPCODE;
+clz TC; ptx_lval.int_value = CLZ_OP; return OPCODE;
+cnot TC; ptx_lval.int_value = CNOT_OP; return OPCODE;
+cos TC; ptx_lval.int_value = COS_OP; return OPCODE;
+cvt TC; ptx_lval.int_value = CVT_OP; return OPCODE;
+cvta TC; ptx_lval.int_value = CVTA_OP; return OPCODE;
+div TC; ptx_lval.int_value = DIV_OP; return OPCODE;
+dp4a TC; ptx_lval.int_value = DP4A_OP; return OPCODE;
+ex2 TC; ptx_lval.int_value = EX2_OP; return OPCODE;
+exit TC; ptx_lval.int_value = EXIT_OP; return OPCODE;
+fma TC; ptx_lval.int_value = FMA_OP; return OPCODE;
+isspacep TC; ptx_lval.int_value = ISSPACEP_OP; return OPCODE;
+ld TC; ptx_lval.int_value = LD_OP; return OPCODE;
+ld.volatile TC; ptx_lval.int_value = LD_OP; return OPCODE;
+ldu TC; ptx_lval.int_value = LDU_OP; return OPCODE;
+lg2 TC; ptx_lval.int_value = LG2_OP; return OPCODE;
+mad24 TC; ptx_lval.int_value = MAD24_OP; return OPCODE;
+mad TC; ptx_lval.int_value = MAD_OP; return OPCODE;
+madc TC; ptx_lval.int_value = MADC_OP; return OPCODE;
+madp TC; ptx_lval.int_value = MADP_OP; return OPCODE;
+max TC; ptx_lval.int_value = MAX_OP; return OPCODE;
+membar TC; ptx_lval.int_value = MEMBAR_OP; return OPCODE;
+min TC; ptx_lval.int_value = MIN_OP; return OPCODE;
+mov TC; ptx_lval.int_value = MOV_OP; return OPCODE;
+mul24 TC; ptx_lval.int_value = MUL24_OP; return OPCODE;
+mul TC; ptx_lval.int_value = MUL_OP; return OPCODE;
+neg TC; ptx_lval.int_value = NEG_OP; return OPCODE;
+nandn TC; ptx_lval.int_value = NANDN_OP; return OPCODE;
+norn TC; ptx_lval.int_value = NORN_OP; return OPCODE;
+not TC; ptx_lval.int_value = NOT_OP; return OPCODE;
+or TC; ptx_lval.int_value = OR_OP; return OPCODE;
+orn TC; ptx_lval.int_value = ORN_OP; return OPCODE;
+pmevent TC; ptx_lval.int_value = PMEVENT_OP; return OPCODE;
+popc TC; ptx_lval.int_value = POPC_OP; return OPCODE;
+prefetch TC; ptx_lval.int_value = PREFETCH_OP; return OPCODE;
+prefetchu TC; ptx_lval.int_value = PREFETCHU_OP; return OPCODE;
+prmt TC; ptx_lval.int_value = PRMT_OP; return OPCODE;
+rcp TC; ptx_lval.int_value = RCP_OP; return OPCODE;
+red TC; ptx_lval.int_value = RED_OP; return OPCODE;
+rem TC; ptx_lval.int_value = REM_OP; return OPCODE;
+ret TC; ptx_lval.int_value = RET_OP; return OPCODE;
+retp TC; ptx_lval.int_value = RETP_OP; return OPCODE;
+rsqrt TC; ptx_lval.int_value = RSQRT_OP; return OPCODE;
+sad TC; ptx_lval.int_value = SAD_OP; return OPCODE;
+selp TC; ptx_lval.int_value = SELP_OP; return OPCODE;
+setp TC; ptx_lval.int_value = SETP_OP; return OPCODE;
+set TC; ptx_lval.int_value = SET_OP; return OPCODE;
+shfl TC; ptx_lval.int_value = SHFL_OP; return OPCODE;
+shl TC; ptx_lval.int_value = SHL_OP; return OPCODE;
+shr TC; ptx_lval.int_value = SHR_OP; return OPCODE;
+sin TC; ptx_lval.int_value = SIN_OP; return OPCODE;
+slct TC; ptx_lval.int_value = SLCT_OP; return OPCODE;
+sqrt TC; ptx_lval.int_value = SQRT_OP; return OPCODE;
+sst TC; ptx_lval.int_value = SST_OP; return OPCODE;
+ssy TC; ptx_lval.int_value = SSY_OP; return OPCODE;
+st TC; ptx_lval.int_value = ST_OP; return OPCODE;
+st.volatile TC; ptx_lval.int_value = ST_OP; return OPCODE;
+sub TC; ptx_lval.int_value = SUB_OP; return OPCODE;
+subc TC; ptx_lval.int_value = SUBC_OP; return OPCODE;
+suld TC; ptx_lval.int_value = SULD_OP; return OPCODE;
+sured TC; ptx_lval.int_value = SURED_OP; return OPCODE;
+surst TC; ptx_lval.int_value = SUST_OP; return OPCODE;
+suq TC; ptx_lval.int_value = SUQ_OP; return OPCODE;
+tex TC; BEGIN(NOT_OPCODE); ptx_lval.int_value = TEX_OP; return OPCODE;
+txq TC; ptx_lval.int_value = TEX_OP; return OPCODE;
+trap TC; ptx_lval.int_value = TRAP_OP; return OPCODE;
+vabsdiff TC; ptx_lval.int_value = VABSDIFF_OP; return OPCODE;
+vadd TC; ptx_lval.int_value = VADD_OP; return OPCODE;
+vmad TC; ptx_lval.int_value = VMAD_OP; return OPCODE;
+vmax TC; ptx_lval.int_value = VMAX_OP; return OPCODE;
+vmin TC; ptx_lval.int_value = VMIN_OP; return OPCODE;
+vset TC; ptx_lval.int_value = VSET_OP; return OPCODE;
+vshl TC; ptx_lval.int_value = VSHL_OP; return OPCODE;
+vshr TC; ptx_lval.int_value = VSHR_OP; return OPCODE;
+vsub TC; ptx_lval.int_value = VSUB_OP; return OPCODE;
+vote TC; ptx_lval.int_value = VOTE_OP; return OPCODE;
+xor TC; ptx_lval.int_value = XOR_OP; return OPCODE;
+nop TC; ptx_lval.int_value = NOP_OP; return OPCODE;
+break TC; ptx_lval.int_value = BREAK_OP; return OPCODE;
+breakaddr TC; ptx_lval.int_value = BREAKADDR_OP; return OPCODE;
+
+"CPTX_END" printf("ENDING CUSTOM PTX.\n"); BEGIN(IN_COMMENT);
+
+<INITIAL,NOT_OPCODE,IN_INST,IN_FUNC_DECL>{
+\.a\.sync TC; ptx_lval.int_value = LOAD_A; return WMMA_DIRECTIVE;
+\.b\.sync TC; ptx_lval.int_value = LOAD_B; return WMMA_DIRECTIVE;
+\.c\.sync TC; ptx_lval.int_value = LOAD_C; return WMMA_DIRECTIVE;
+\.d\.sync TC; ptx_lval.int_value = STORE_D; return WMMA_DIRECTIVE;
+\.mma\.sync TC;ptx_lval.int_value=MMA; return WMMA_DIRECTIVE;
+
+\.row TC; ptx_lval.int_value = ROW; return LAYOUT;
+\.col TC; ptx_lval.int_value = COL; return LAYOUT;
+\.m16n16k16 TC; ptx_lval.int_value = M16N16K16; return CONFIGURATION;
+\.f4e TC; return PRMT_F4E_MODE;
+\.b4e TC; return PRMT_B4E_MODE;
+\.rc8 TC; return PRMT_RC8_MODE;
+\.ecl TC; return PRMT_ECL_MODE;
+\.ecr TC; return PRMT_ECR_MODE;
+\.rc16 TC; return PRMT_RC16_MODE;
+
+\.align TC; return ALIGN_DIRECTIVE;
+\.branchtargets TC; return BRANCHTARGETS_DIRECTIVE;
+\.byte TC; return BYTE_DIRECTIVE; /* not in PTX 2.1 */
+\.callprototype TC; return CALLPROTOTYPE_DIRECTIVE;
+\.calltargets TC; return CALLTARGETS_DIRECTIVE;
+\.const\[[0-9]+\] TC; ptx_lval.int_value = atoi(yytext+7); return CONST_DIRECTIVE;
+\.const TC; ptx_lval.int_value = 0; return CONST_DIRECTIVE;
+\.entry TC; return ENTRY_DIRECTIVE;
+\.extern TC; return EXTERN_DIRECTIVE;
+\.file TC; BEGIN(INITIAL); return FILE_DIRECTIVE;
+\.func TC; BEGIN(IN_FUNC_DECL); return FUNC_DIRECTIVE; // blocking opcode parsing in case the function has the same name as an opcode (e.g. sin(), cos())
+\.global TC; return GLOBAL_DIRECTIVE;
+\.global.volatile TC; return GLOBAL_DIRECTIVE; //TODO: fix this!
+\.local TC; return LOCAL_DIRECTIVE;
+\.loc TC; return LOC_DIRECTIVE;
+\.maxnctapersm TC; return MAXNCTAPERSM_DIRECTIVE;
+\.maxnreg TC; return MAXNNREG_DIRECTIVE;
+\.maxntid TC; return MAXNTID_DIRECTIVE;
+\.minnctapersm TC; return MINNCTAPERSM_DIRECTIVE;
+\.param TC; return PARAM_DIRECTIVE;
+\.pragma TC; return PRAGMA_DIRECTIVE;
+\.reg TC; return REG_DIRECTIVE;
+\.reqntid TC; return REQNTID_DIRECTIVE;
+\.section TC; return SECTION_DIRECTIVE;
+\.shared TC; return SHARED_DIRECTIVE;
+\.sreg TC; return SREG_DIRECTIVE;
+\.sstarr TC; return SSTARR_DIRECTIVE;
+\.struct TC; return STRUCT_DIRECTIVE;
+\.surf TC; return SURF_DIRECTIVE; /* not in PTX 2.1 */
+\.target TC; return TARGET_DIRECTIVE;
+\.tex TC; BEGIN(NOT_OPCODE); return TEX_DIRECTIVE;
+\.union TC; return UNION_DIRECTIVE; /* not in PTX 2.1 */
+\.version TC; return VERSION_DIRECTIVE;
+\.visible TC; return VISIBLE_DIRECTIVE;
+\.weak TC; return WEAK_DIRECTIVE;
+\.address_size TC; return ADDRESS_SIZE_DIRECTIVE;
+\.weak TC; return WEAK_DIRECTIVE;
+
+\.constptr TC; return CONSTPTR_DIRECTIVE; /* Ptx plus directive for pointer to constant memory */
+\.ptr TC; return PTR_DIRECTIVE; /* Added for new OpenCL genrated code */
+
+"%clock" TC; ptx_lval.int_value = CLOCK_REG; return SPECIAL_REGISTER;
+"%halfclock" TC; ptx_lval.int_value = HALFCLOCK_ID; return SPECIAL_REGISTER;
+"%clock64" TC; ptx_lval.int_value = CLOCK64_REG; return SPECIAL_REGISTER;
+"%ctaid" TC; ptx_lval.int_value = CTAID_REG; return SPECIAL_REGISTER;
+"%envreg"[0-9]+ TC; sscanf(yytext+7,"%u",&ptx_lval.int_value); ptx_lval.int_value<<=16; ptx_lval.int_value += ENVREG_REG; return SPECIAL_REGISTER;
+"%gridid" TC; ptx_lval.int_value = GRIDID_REG; return SPECIAL_REGISTER;
+"%laneid" TC; ptx_lval.int_value = LANEID_REG; return SPECIAL_REGISTER;
+"%lanemask_eq" TC; ptx_lval.int_value = LANEMASK_EQ_REG; return SPECIAL_REGISTER;
+"%lanemask_le" TC; ptx_lval.int_value = LANEMASK_LE_REG; return SPECIAL_REGISTER;
+"%lanemask_lt" TC; ptx_lval.int_value = LANEMASK_LT_REG; return SPECIAL_REGISTER;
+"%lanemask_ge" TC; ptx_lval.int_value = LANEMASK_GE_REG; return SPECIAL_REGISTER;
+"%lanemask_gt" TC; ptx_lval.int_value = LANEMASK_GT_REG; return SPECIAL_REGISTER;
+"%nctaid" TC; ptx_lval.int_value = NCTAID_REG; return SPECIAL_REGISTER;
+"%ntid" TC; ptx_lval.int_value = NTID_REG; return SPECIAL_REGISTER;
+"%nsmid" TC; ptx_lval.int_value = NSMID_REG; return SPECIAL_REGISTER;
+"%nwarpid" TC; ptx_lval.int_value = NWARPID_REG; return SPECIAL_REGISTER;
+"%pm"[0-3] TC; sscanf(yytext+3,"%u",&ptx_lval.int_value); ptx_lval.int_value<<=16; ptx_lval.int_value += PM_REG; return SPECIAL_REGISTER;
+"%smid" TC; ptx_lval.int_value = SMID_REG; return SPECIAL_REGISTER;
+"%tid" TC; ptx_lval.int_value = TID_REG; return SPECIAL_REGISTER;
+"%warpid" TC; ptx_lval.int_value = WARPID_REG; return SPECIAL_REGISTER;
+"WARP_SZ" TC; ptx_lval.int_value = WARPSZ_REG; return SPECIAL_REGISTER;
+
+[a-zA-Z_][a-zA-Z0-9_$]* TC; ptx_lval.string_value = strdup(yytext); return IDENTIFIER;
+[$%][a-zA-Z0-9_$]+ TC; ptx_lval.string_value = strdup(yytext); return IDENTIFIER;
+
+[0-9]+\.[0-9]+ TC; sscanf(yytext,"%lf", &ptx_lval.double_value); return DOUBLE_OPERAND;
+
+0[xX][0-9a-fA-F]+U? TC; CHECK_UNSIGNED; sscanf(yytext,"%x", &ptx_lval.int_value); return INT_OPERAND;
+0[0-7]+U? TC; printf("GPGPU-Sim: ERROR ** parsing octal not (yet) implemented\n"); abort(); return INT_OPERAND;
+0[bB][01]+U? TC; printf("GPGPU-Sim: ERROR ** parsing binary not (yet) implemented\n"); abort(); return INT_OPERAND;
+[-]?[0-9]+U? TC; CHECK_UNSIGNED; ptx_lval.int_value = atoi(yytext); return INT_OPERAND;
+
+0[fF][0-9a-fA-F]{8} TC; sscanf(yytext+2,"%x", (unsigned*)(void*)&ptx_lval.float_value); return FLOAT_OPERAND;
+0[dD][0-9a-fA-F]{16} TC; sscanf(yytext+2,"%Lx", (unsigned long long*)(void*)&ptx_lval.double_value); return DOUBLE_OPERAND;
+
+\.s8 TC; return S8_TYPE;
+\.s16 TC; return S16_TYPE;
+\.s32 TC; return S32_TYPE;
+\.s64 TC; return S64_TYPE;
+\.u8 TC; return U8_TYPE;
+\.u16 TC; return U16_TYPE;
+\.u32 TC; return U32_TYPE;
+\.u64 TC; return U64_TYPE;
+\.f16 TC; return F16_TYPE;
+\.f16x2 TC; return F16_TYPE; /* TODO: figure out what this should really be */
+\.f32 TC; return F32_TYPE;
+\.f64 TC; return F64_TYPE;
+\.ff64 TC; return FF64_TYPE;
+\.b8 TC; return B8_TYPE;
+\.b16 TC; return B16_TYPE;
+\.b32 TC; return B32_TYPE;
+\.b64 TC; return B64_TYPE;
+\.bb64 TC; return BB64_TYPE;
+\.bb128 TC; return BB128_TYPE;
+\.pred TC; return PRED_TYPE;
+
+\.texref TC; BEGIN(NOT_OPCODE); return TEXREF_TYPE;
+\.samplerref TC; return SAMPLERREF_TYPE;
+\.surfref TC; return SURFREF_TYPE;
+
+\.v2 TC; return V2_TYPE;
+\.v3 TC; return V3_TYPE;
+\.v4 TC; return V4_TYPE;
+
+\.half TC; return HALF_OPTION; /* ptxplus */
+\.cc TC; return EXTP_OPTION; /* extended precision option */
+
+\.equ TC; return EQU_OPTION;
+\.neu TC; return NEU_OPTION;
+\.ltu TC; return LTU_OPTION;
+\.leu TC; return LEU_OPTION;
+\.gtu TC; return GTU_OPTION;
+\.geu TC; return GEU_OPTION;
+\.num TC; return NUM_OPTION;
+\.nan TC; return NAN_OPTION;
+
+\.sat TC; return SAT_OPTION;
+
+\.eq TC; return EQ_OPTION;
+\.ne TC; return NE_OPTION;
+\.lt TC; return LT_OPTION;
+\.le TC; return LE_OPTION;
+\.gt TC; return GT_OPTION;
+\.ge TC; return GE_OPTION;
+\.cf TC; return CF_OPTION;
+\.sf TC; return SF_OPTION;
+\.nsf TC; return NSF_OPTION;
+
+\.lo TC; return LO_OPTION;
+\.ls TC; return LS_OPTION;
+\.hi TC; return HI_OPTION;
+\.hs TC; return HS_OPTION;
+
+
+\.rni TC; return RNI_OPTION;
+\.rzi TC; return RZI_OPTION;
+\.rmi TC; return RMI_OPTION;
+\.rpi TC; return RPI_OPTION;
+
+\.rn TC; return RN_OPTION;
+\.rz TC; return RZ_OPTION;
+\.rm TC; return RM_OPTION;
+\.rp TC; return RP_OPTION;
+
+\.ftz TC; return FTZ_OPTION;
+
+\.neg TC; return NEG_OPTION;
+
+\.wide TC; return WIDE_OPTION;
+\.uni TC; return UNI_OPTION;
+
+\.sync TC; return SYNC_OPTION;
+\.arrive TC; return ARRIVE_OPTION;
+\.red TC; return RED_OPTION;
+
+
+\.approx TC; return APPROX_OPTION;
+\.full TC; return FULL_OPTION;
+
+\.any TC; return ANY_OPTION;
+\.all TC; return ALL_OPTION;
+\.ballot TC; return BALLOT_OPTION;
+\.gl TC; return GLOBAL_OPTION;
+\.cta TC; return CTA_OPTION;
+\.sys TC; return SYS_OPTION;
+
+\.exit TC; return EXIT_OPTION;
+
+\.abs TC; return ABS_OPTION;
+
+\.to TC; return TO_OPTION;
+
+\.ca TC; return CA_OPTION;
+\.cg TC; return CG_OPTION;
+\.cs TC; return CS_OPTION;
+\.lu TC; return LU_OPTION;
+\.cv TC; return CV_OPTION;
+
+\.wb TC; return WB_OPTION;
+\.wt TC; return WT_OPTION;
+
+\.nc TC; return NC_OPTION;
+
+\.up TC; return UP_OPTION;
+\.down TC; return DOWN_OPTION;
+\.bfly TC; return BFLY_OPTION;
+\.idx TC; return IDX_OPTION;
+
+\.popc TC; return ATOMIC_POPC;
+\.and TC; return ATOMIC_AND;
+\.or TC; return ATOMIC_OR;
+\.xor TC; return ATOMIC_XOR;
+\.cas TC; return ATOMIC_CAS;
+\.exch TC; return ATOMIC_EXCH;
+\.add TC; return ATOMIC_ADD;
+\.inc TC; return ATOMIC_INC;
+\.dec TC; return ATOMIC_DEC;
+\.min TC; return ATOMIC_MIN;
+\.max TC; return ATOMIC_MAX;
+
+
+
+\.1d TC; return GEOM_MODIFIER_1D;
+\.2d TC; return GEOM_MODIFIER_2D;
+\.3d TC; return GEOM_MODIFIER_3D;
+
+\.0 TC; ptx_lval.int_value = 0; return DIMENSION_MODIFIER;
+\.1 TC; ptx_lval.int_value = 1; return DIMENSION_MODIFIER;
+\.2 TC; ptx_lval.int_value = 2; return DIMENSION_MODIFIER;
+\.x TC; ptx_lval.int_value = 0; return DIMENSION_MODIFIER;
+\.y TC; ptx_lval.int_value = 1; return DIMENSION_MODIFIER;
+\.z TC; ptx_lval.int_value = 2; return DIMENSION_MODIFIER;
+
+"-" TC; return MINUS;
+"+" TC; return PLUS;
+"," TC; return COMMA;
+"@" TC; return PRED;
+"|" TC; return PIPE;
+"[" TC; return LEFT_SQUARE_BRACKET;
+"]" TC; return RIGHT_SQUARE_BRACKET;
+"<" TC; return LEFT_ANGLE_BRACKET;
+">" TC; return RIGHT_ANGLE_BRACKET;
+"(" TC; return LEFT_PAREN;
+")" TC; return RIGHT_PAREN;
+":" TC; BEGIN(INITIAL); return COLON;
+";" TC; BEGIN(INITIAL); return SEMI_COLON;
+"!" TC; return EXCLAMATION;
+"=" TC; return EQUALS;
+"}" TC; return RIGHT_BRACE;
+\. TC; return PERIOD;
+"/" TC; return BACKSLASH;
+
+"//"[^\n]* TC; // eat single
+
+\n.* col=0; strncpy(linebuf, yytext + 1, LINEBUF_SIZE); yyless( 1 );
+
+" " TC;
+"\t" TC;
+
+
+}
+
+<IN_FUNC_DECL>"{" TC; BEGIN(INITIAL); return LEFT_BRACE; // starting a statement block (allow next token to be parsed as an opcode)
+<INITIAL,NOT_OPCODE>"{" TC; return LEFT_BRACE; // starting a vector operand (next token cannot be opcode)
+
+<INITIAL>{
+"/*" BEGIN(IN_COMMENT);
+}
+<IN_COMMENT>{
+"*/" BEGIN(INITIAL);
+"CPTX_BEGIN" printf("BEGINNING CUSTOM PTX.\n"); BEGIN(INITIAL);
+[^C*\n]+ // eat comment in chunks
+"C" // eat the lone C
+"*" // eat the lone star
+\n TC;
+}
+
+<INITIAL>{
+"\"" BEGIN(IN_STRING);
+}
+<IN_STRING>{
+"\"" TC; BEGIN(INITIAL); return STRING;
+[^\"]* TC; ptx_lval.string_value = strdup(yytext);
+}
+
+<*>\t@@DWARF.*\n
+
+<INITIAL,NOT_OPCODE,IN_FUNC_DECL>. TC; ptx_error((const char*)NULL);
+%%
+
+extern int g_error_detected;
+extern const char *g_filename;
+
+int ptx_error( const char *s )
+{
+ int i;
+ g_error_detected = 1;
+ fflush(stdout);
+ if( s != NULL )
+ printf("%s:%u: Syntax error:\n\n", g_filename, ptx_lineno );
+ printf(" %s\n", linebuf );
+ printf(" ");
+ for( i=0; i < col-1; i++ ) {
+ if( linebuf[i] == '\t' ) printf("\t");
+ else printf(" ");
+ }
+
+ printf("^\n\n");
+ fflush(stdout);
+ //exit(1);
+ return 0;
+}
diff --git a/cuobjdump_to_ptxplus/ptx.y b/cuobjdump_to_ptxplus/ptx.y
new file mode 100644
index 0000000..45392fb
--- /dev/null
+++ b/cuobjdump_to_ptxplus/ptx.y
@@ -0,0 +1,629 @@
+/*
+Copyright (c) 2009-2011, Tor M. Aamodt
+The University of British Columbia
+All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are met:
+
+Redistributions of source code must retain the above copyright notice, this
+list of conditions and the following disclaimer.
+Redistributions in binary form must reproduce the above copyright notice, this
+list of conditions and the following disclaimer in the documentation and/or
+other materials provided with the distribution.
+Neither the name of The University of British Columbia nor the names of its
+contributors may be used to endorse or promote products derived from this
+software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
+ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
+FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+*/
+
+%union {
+ double double_value;
+ float float_value;
+ int int_value;
+ char * string_value;
+ void * ptr_value;
+}
+
+%token <string_value> STRING
+%token <int_value> OPCODE
+%token <int_value> WMMA_DIRECTIVE
+%token <int_value> LAYOUT
+%token <int_value> CONFIGURATION
+%token ALIGN_DIRECTIVE
+%token BRANCHTARGETS_DIRECTIVE
+%token BYTE_DIRECTIVE
+%token CALLPROTOTYPE_DIRECTIVE
+%token CALLTARGETS_DIRECTIVE
+%token <int_value> CONST_DIRECTIVE
+%token CONSTPTR_DIRECTIVE
+%token PTR_DIRECTIVE
+%token ENTRY_DIRECTIVE
+%token EXTERN_DIRECTIVE
+%token FILE_DIRECTIVE
+%token FUNC_DIRECTIVE
+%token GLOBAL_DIRECTIVE
+%token LOCAL_DIRECTIVE
+%token LOC_DIRECTIVE
+%token MAXNCTAPERSM_DIRECTIVE
+%token MAXNNREG_DIRECTIVE
+%token MAXNTID_DIRECTIVE
+%token MINNCTAPERSM_DIRECTIVE
+%token PARAM_DIRECTIVE
+%token PRAGMA_DIRECTIVE
+%token REG_DIRECTIVE
+%token REQNTID_DIRECTIVE
+%token SECTION_DIRECTIVE
+%token SHARED_DIRECTIVE
+%token SREG_DIRECTIVE
+%token SSTARR_DIRECTIVE
+%token STRUCT_DIRECTIVE
+%token SURF_DIRECTIVE
+%token TARGET_DIRECTIVE
+%token TEX_DIRECTIVE
+%token UNION_DIRECTIVE
+%token VERSION_DIRECTIVE
+%token ADDRESS_SIZE_DIRECTIVE
+%token VISIBLE_DIRECTIVE
+%token WEAK_DIRECTIVE
+%token <string_value> IDENTIFIER
+%token <int_value> INT_OPERAND
+%token <float_value> FLOAT_OPERAND
+%token <double_value> DOUBLE_OPERAND
+%token S8_TYPE
+%token S16_TYPE
+%token S32_TYPE
+%token S64_TYPE
+%token U8_TYPE
+%token U16_TYPE
+%token U32_TYPE
+%token U64_TYPE
+%token F16_TYPE
+%token F32_TYPE
+%token F64_TYPE
+%token FF64_TYPE
+%token B8_TYPE
+%token B16_TYPE
+%token B32_TYPE
+%token B64_TYPE
+%token BB64_TYPE
+%token BB128_TYPE
+%token PRED_TYPE
+%token TEXREF_TYPE
+%token SAMPLERREF_TYPE
+%token SURFREF_TYPE
+%token V2_TYPE
+%token V3_TYPE
+%token V4_TYPE
+%token COMMA
+%token PRED
+%token HALF_OPTION
+%token EXTP_OPTION
+%token EQ_OPTION
+%token NE_OPTION
+%token LT_OPTION
+%token LE_OPTION
+%token GT_OPTION
+%token GE_OPTION
+%token LO_OPTION
+%token LS_OPTION
+%token HI_OPTION
+%token HS_OPTION
+%token EQU_OPTION
+%token NEU_OPTION
+%token LTU_OPTION
+%token LEU_OPTION
+%token GTU_OPTION
+%token GEU_OPTION
+%token NUM_OPTION
+%token NAN_OPTION
+%token CF_OPTION
+%token SF_OPTION
+%token NSF_OPTION
+%token LEFT_SQUARE_BRACKET
+%token RIGHT_SQUARE_BRACKET
+%token WIDE_OPTION
+%token <int_value> SPECIAL_REGISTER
+%token MINUS
+%token PLUS
+%token COLON
+%token SEMI_COLON
+%token EXCLAMATION
+%token PIPE
+%token RIGHT_BRACE
+%token LEFT_BRACE
+%token EQUALS
+%token PERIOD
+%token BACKSLASH
+%token <int_value> DIMENSION_MODIFIER
+%token RN_OPTION
+%token RZ_OPTION
+%token RM_OPTION
+%token RP_OPTION
+%token RNI_OPTION
+%token RZI_OPTION
+%token RMI_OPTION
+%token RPI_OPTION
+%token UNI_OPTION
+%token GEOM_MODIFIER_1D
+%token GEOM_MODIFIER_2D
+%token GEOM_MODIFIER_3D
+%token SAT_OPTION
+%token FTZ_OPTION
+%token NEG_OPTION
+%token SYNC_OPTION
+%token RED_OPTION
+%token ARRIVE_OPTION
+%token ATOMIC_POPC
+%token ATOMIC_AND
+%token ATOMIC_OR
+%token ATOMIC_XOR
+%token ATOMIC_CAS
+%token ATOMIC_EXCH
+%token ATOMIC_ADD
+%token ATOMIC_INC
+%token ATOMIC_DEC
+%token ATOMIC_MIN
+%token ATOMIC_MAX
+%token LEFT_ANGLE_BRACKET
+%token RIGHT_ANGLE_BRACKET
+%token LEFT_PAREN
+%token RIGHT_PAREN
+%token APPROX_OPTION
+%token FULL_OPTION
+%token ANY_OPTION
+%token ALL_OPTION
+%token BALLOT_OPTION
+%token GLOBAL_OPTION
+%token CTA_OPTION
+%token SYS_OPTION
+%token EXIT_OPTION
+%token ABS_OPTION
+%token TO_OPTION
+%token CA_OPTION;
+%token CG_OPTION;
+%token CS_OPTION;
+%token LU_OPTION;
+%token CV_OPTION;
+%token WB_OPTION;
+%token WT_OPTION;
+%token NC_OPTION;
+%token UP_OPTION;
+%token DOWN_OPTION;
+%token BFLY_OPTION;
+%token IDX_OPTION;
+%token PRMT_F4E_MODE;
+%token PRMT_B4E_MODE;
+%token PRMT_RC8_MODE;
+%token PRMT_RC16_MODE;
+%token PRMT_ECL_MODE;
+%token PRMT_ECR_MODE;
+
+%type <int_value> function_decl_header
+%type <ptr_value> function_decl
+
+%{
+ #include "ptx_parser.h"
+ #include <stdlib.h>
+ #include <string.h>
+ #include <math.h>
+ void syntax_not_implemented();
+ extern int g_func_decl;
+ int ptx_lex(void);
+ int ptx_error(const char *);
+%}
+
+%%
+
+input: /* empty */
+ | input directive_statement
+ | input function_defn
+ | input function_decl
+ ;
+
+function_defn: function_decl { set_symtab($1); func_header(".skip"); } statement_block { end_function(); }
+ | function_decl { set_symtab($1); } block_spec_list { func_header(".skip"); } statement_block { end_function(); }
+ ;
+
+block_spec: MAXNTID_DIRECTIVE INT_OPERAND COMMA INT_OPERAND COMMA INT_OPERAND {func_header_info_int(".maxntid", $2);
+ func_header_info_int(",", $4);
+ func_header_info_int(",", $6);
+ maxnt_id($2, $4, $6);}
+ | MINNCTAPERSM_DIRECTIVE INT_OPERAND { func_header_info_int(".minnctapersm", $2); printf("GPGPU-Sim: Warning: .minnctapersm ignored. \n"); }
+ | MAXNCTAPERSM_DIRECTIVE INT_OPERAND { func_header_info_int(".maxnctapersm", $2); printf("GPGPU-Sim: Warning: .maxnctapersm ignored. \n"); }
+ ;
+
+block_spec_list: block_spec
+ | block_spec_list block_spec
+ ;
+
+function_decl: function_decl_header LEFT_PAREN { start_function($1); func_header_info("(");} param_entry RIGHT_PAREN {func_header_info(")");} function_ident_param { $$ = reset_symtab(); }
+ | function_decl_header { start_function($1); } function_ident_param { $$ = reset_symtab(); }
+ | function_decl_header { start_function($1); add_function_name(""); g_func_decl=0; $$ = reset_symtab(); }
+ ;
+
+function_ident_param: IDENTIFIER { add_function_name($1); } LEFT_PAREN {func_header_info("(");} param_list RIGHT_PAREN { g_func_decl=0; func_header_info(")"); }
+ | IDENTIFIER { add_function_name($1); g_func_decl=0; }
+ ;
+
+function_decl_header: ENTRY_DIRECTIVE { $$ = 1; g_func_decl=1; func_header(".entry"); }
+ | VISIBLE_DIRECTIVE ENTRY_DIRECTIVE { $$ = 1; g_func_decl=1; func_header(".entry"); }
+ | WEAK_DIRECTIVE ENTRY_DIRECTIVE { $$ = 1; g_func_decl=1; func_header(".entry"); }
+ | FUNC_DIRECTIVE { $$ = 0; g_func_decl=1; func_header(".func"); }
+ | VISIBLE_DIRECTIVE FUNC_DIRECTIVE { $$ = 0; g_func_decl=1; func_header(".func"); }
+ | WEAK_DIRECTIVE FUNC_DIRECTIVE { $$ = 0; g_func_decl=1; func_header(".func"); }
+ | EXTERN_DIRECTIVE FUNC_DIRECTIVE { $$ = 2; g_func_decl=1; func_header(".func"); }
+ | WEAK_DIRECTIVE FUNC_DIRECTIVE { $$ = 0; g_func_decl=1; func_header(".func"); }
+ ;
+
+param_list: /*empty*/
+ | param_entry { add_directive(); }
+ | param_list COMMA {func_header_info(",");} param_entry { add_directive(); }
+
+param_entry: PARAM_DIRECTIVE { add_space_spec(param_space_unclassified,0); } variable_spec ptr_spec identifier_spec { add_function_arg(); }
+ | REG_DIRECTIVE { add_space_spec(reg_space,0); } variable_spec identifier_spec { add_function_arg(); }
+
+ptr_spec: /*empty*/
+ | PTR_DIRECTIVE ptr_space_spec ptr_align_spec
+ | PTR_DIRECTIVE ptr_align_spec
+
+ptr_space_spec: GLOBAL_DIRECTIVE { add_ptr_spec(global_space); }
+ | LOCAL_DIRECTIVE { add_ptr_spec(local_space); }
+ | SHARED_DIRECTIVE { add_ptr_spec(shared_space); }
+ | CONST_DIRECTIVE { add_ptr_spec(global_space); }
+
+ptr_align_spec: ALIGN_DIRECTIVE INT_OPERAND
+
+statement_block: LEFT_BRACE statement_list RIGHT_BRACE
+
+statement_list: directive_statement { add_directive(); }
+ | instruction_statement { add_instruction(); }
+ | statement_list directive_statement { add_directive(); }
+ | statement_list instruction_statement { add_instruction(); }
+ | statement_list {start_inst_group();} statement_block {end_inst_group();}
+ | {start_inst_group();} statement_block {end_inst_group();}
+ ;
+
+directive_statement: variable_declaration SEMI_COLON
+ | VERSION_DIRECTIVE DOUBLE_OPERAND { add_version_info($2, 0); }
+ | VERSION_DIRECTIVE DOUBLE_OPERAND PLUS { add_version_info($2,1); }
+ | ADDRESS_SIZE_DIRECTIVE INT_OPERAND {/*Do nothing*/}
+ | TARGET_DIRECTIVE IDENTIFIER COMMA IDENTIFIER { target_header2($2,$4); }
+ | TARGET_DIRECTIVE IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER { target_header3($2,$4,$6); }
+ | TARGET_DIRECTIVE IDENTIFIER { target_header($2); }
+ | FILE_DIRECTIVE INT_OPERAND STRING { add_file($2,$3); }
+ | FILE_DIRECTIVE INT_OPERAND STRING COMMA INT_OPERAND COMMA INT_OPERAND { add_file($2,$3); }
+ | LOC_DIRECTIVE INT_OPERAND INT_OPERAND INT_OPERAND
+ | PRAGMA_DIRECTIVE STRING SEMI_COLON { add_pragma($2); }
+ | function_decl SEMI_COLON {/*Do nothing*/}
+ ;
+
+variable_declaration: variable_spec identifier_list { add_variables(); }
+ | variable_spec identifier_spec EQUALS initializer_list { add_variables(); }
+ | variable_spec identifier_spec EQUALS literal_operand { add_variables(); }
+ | CONSTPTR_DIRECTIVE IDENTIFIER COMMA IDENTIFIER COMMA INT_OPERAND { add_constptr($2, $4, $6); }
+ ;
+
+variable_spec: var_spec_list { set_variable_type(); }
+
+identifier_list: identifier_spec
+ | identifier_list COMMA identifier_spec;
+
+identifier_spec: IDENTIFIER { add_identifier($1,0,NON_ARRAY_IDENTIFIER); func_header_info($1);}
+ | IDENTIFIER LEFT_ANGLE_BRACKET INT_OPERAND RIGHT_ANGLE_BRACKET { func_header_info($1); func_header_info_int("<", $3); func_header_info(">");
+ int i,lbase,l;
+ char *id = NULL;
+ lbase = strlen($1);
+ for( i=0; i < $3; i++ ) {
+ l = lbase + (int)log10(i+1)+10;
+ id = (char*) malloc(l);
+ snprintf(id,l,"%s%u",$1,i);
+ add_identifier(id,0,NON_ARRAY_IDENTIFIER);
+ }
+ free($1);
+ }
+ | IDENTIFIER LEFT_SQUARE_BRACKET RIGHT_SQUARE_BRACKET { add_identifier($1,0,ARRAY_IDENTIFIER_NO_DIM); func_header_info($1); func_header_info("["); func_header_info("]");}
+ | IDENTIFIER LEFT_SQUARE_BRACKET INT_OPERAND RIGHT_SQUARE_BRACKET { add_identifier($1,$3,ARRAY_IDENTIFIER); func_header_info($1); func_header_info_int("[",$3); func_header_info("]");}
+ ;
+
+var_spec_list: var_spec
+ | var_spec_list var_spec;
+
+var_spec: space_spec
+ | type_spec
+ | align_spec
+ | VISIBLE_DIRECTIVE
+ | EXTERN_DIRECTIVE { add_extern_spec(); }
+ | WEAK_DIRECTIVE
+ ;
+
+align_spec: ALIGN_DIRECTIVE INT_OPERAND { add_alignment_spec($2); }
+
+space_spec: REG_DIRECTIVE { add_space_spec(reg_space,0); }
+ | SREG_DIRECTIVE { add_space_spec(reg_space,0); }
+ | addressable_spec
+ ;
+
+addressable_spec: CONST_DIRECTIVE { add_space_spec(const_space,$1); }
+ | GLOBAL_DIRECTIVE { add_space_spec(global_space,0); }
+ | LOCAL_DIRECTIVE { add_space_spec(local_space,0); }
+ | PARAM_DIRECTIVE { add_space_spec(param_space_unclassified,0); }
+ | SHARED_DIRECTIVE { add_space_spec(shared_space,0); }
+ | SSTARR_DIRECTIVE { add_space_spec(sstarr_space,0); }
+ | SURF_DIRECTIVE { add_space_spec(surf_space,0); }
+ | TEX_DIRECTIVE { add_space_spec(tex_space,0); }
+ ;
+
+type_spec: scalar_type
+ | vector_spec scalar_type
+ ;
+
+vector_spec: V2_TYPE { add_option(V2_TYPE); func_header_info(".v2");}
+ | V3_TYPE { add_option(V3_TYPE); func_header_info(".v3");}
+ | V4_TYPE { add_option(V4_TYPE); func_header_info(".v4");}
+ ;
+
+scalar_type: S8_TYPE { add_scalar_type_spec( S8_TYPE ); }
+ | S16_TYPE { add_scalar_type_spec( S16_TYPE ); }
+ | S32_TYPE { add_scalar_type_spec( S32_TYPE ); }
+ | S64_TYPE { add_scalar_type_spec( S64_TYPE ); }
+ | U8_TYPE { add_scalar_type_spec( U8_TYPE ); }
+ | U16_TYPE { add_scalar_type_spec( U16_TYPE ); }
+ | U32_TYPE { add_scalar_type_spec( U32_TYPE ); }
+ | U64_TYPE { add_scalar_type_spec( U64_TYPE ); }
+ | F16_TYPE { add_scalar_type_spec( F16_TYPE ); }
+ | F32_TYPE { add_scalar_type_spec( F32_TYPE ); }
+ | F64_TYPE { add_scalar_type_spec( F64_TYPE ); }
+ | FF64_TYPE { add_scalar_type_spec( FF64_TYPE ); }
+ | B8_TYPE { add_scalar_type_spec( B8_TYPE ); }
+ | B16_TYPE { add_scalar_type_spec( B16_TYPE ); }
+ | B32_TYPE { add_scalar_type_spec( B32_TYPE ); }
+ | B64_TYPE { add_scalar_type_spec( B64_TYPE ); }
+ | BB64_TYPE { add_scalar_type_spec( BB64_TYPE ); }
+ | BB128_TYPE { add_scalar_type_spec( BB128_TYPE ); }
+ | PRED_TYPE { add_scalar_type_spec( PRED_TYPE ); }
+ | TEXREF_TYPE { add_scalar_type_spec( TEXREF_TYPE ); }
+ | SAMPLERREF_TYPE { add_scalar_type_spec( SAMPLERREF_TYPE ); }
+ | SURFREF_TYPE { add_scalar_type_spec( SURFREF_TYPE ); }
+ ;
+
+initializer_list: LEFT_BRACE literal_list RIGHT_BRACE { add_array_initializer(); }
+ | LEFT_BRACE initializer_list RIGHT_BRACE { syntax_not_implemented(); }
+
+literal_list: literal_operand
+ | literal_list COMMA literal_operand;
+
+instruction_statement: instruction SEMI_COLON
+ | IDENTIFIER COLON { add_label($1); }
+ | pred_spec instruction SEMI_COLON;
+
+instruction: opcode_spec LEFT_PAREN operand RIGHT_PAREN { set_return(); } COMMA operand COMMA LEFT_PAREN operand_list RIGHT_PAREN
+ | opcode_spec operand COMMA LEFT_PAREN operand_list RIGHT_PAREN
+ | opcode_spec operand COMMA LEFT_PAREN RIGHT_PAREN
+ | opcode_spec operand_list
+ | opcode_spec
+ ;
+
+opcode_spec: OPCODE { add_opcode($1); } option_list
+ | OPCODE { add_opcode($1); }
+
+pred_spec: PRED IDENTIFIER { add_pred($2,0, -1); }
+ | PRED EXCLAMATION IDENTIFIER { add_pred($3,1, -1); }
+ | PRED IDENTIFIER LT_OPTION { add_pred($2,0,1); }
+ | PRED IDENTIFIER EQ_OPTION { add_pred($2,0,2); }
+ | PRED IDENTIFIER LE_OPTION { add_pred($2,0,3); }
+ | PRED IDENTIFIER NE_OPTION { add_pred($2,0,5); }
+ | PRED IDENTIFIER GE_OPTION { add_pred($2,0,6); }
+ | PRED IDENTIFIER EQU_OPTION { add_pred($2,0,10); }
+ | PRED IDENTIFIER GTU_OPTION { add_pred($2,0,12); }
+ | PRED IDENTIFIER NEU_OPTION { add_pred($2,0,13); }
+ | PRED IDENTIFIER CF_OPTION { add_pred($2,0,17); }
+ | PRED IDENTIFIER SF_OPTION { add_pred($2,0,19); }
+ | PRED IDENTIFIER NSF_OPTION { add_pred($2,0,28); }
+ ;
+
+option_list: option
+ | option option_list ;
+
+option: type_spec
+ | compare_spec
+ | addressable_spec
+ | rounding_mode
+ | wmma_spec
+ | prmt_spec
+ | SYNC_OPTION { add_option(SYNC_OPTION); }
+ | ARRIVE_OPTION { add_option(ARRIVE_OPTION); }
+ | RED_OPTION { add_option(RED_OPTION); }
+ | UNI_OPTION { add_option(UNI_OPTION); }
+ | WIDE_OPTION { add_option(WIDE_OPTION); }
+ | ANY_OPTION { add_option(ANY_OPTION); }
+ | ALL_OPTION { add_option(ALL_OPTION); }
+ | BALLOT_OPTION { add_option(BALLOT_OPTION); }
+ | GLOBAL_OPTION { add_option(GLOBAL_OPTION); }
+ | CTA_OPTION { add_option(CTA_OPTION); }
+ | SYS_OPTION { add_option(SYS_OPTION); }
+ | GEOM_MODIFIER_1D { add_option(GEOM_MODIFIER_1D); }
+ | GEOM_MODIFIER_2D { add_option(GEOM_MODIFIER_2D); }
+ | GEOM_MODIFIER_3D { add_option(GEOM_MODIFIER_3D); }
+ | SAT_OPTION { add_option(SAT_OPTION); }
+ | FTZ_OPTION { add_option(FTZ_OPTION); }
+ | NEG_OPTION { add_option(NEG_OPTION); }
+ | APPROX_OPTION { add_option(APPROX_OPTION); }
+ | FULL_OPTION { add_option(FULL_OPTION); }
+ | EXIT_OPTION { add_option(EXIT_OPTION); }
+ | ABS_OPTION { add_option(ABS_OPTION); }
+ | atomic_operation_spec ;
+ | TO_OPTION { add_option(TO_OPTION); }
+ | HALF_OPTION { add_option(HALF_OPTION); }
+ | EXTP_OPTION { add_option(EXTP_OPTION); }
+ | CA_OPTION { add_option(CA_OPTION); }
+ | CG_OPTION { add_option(CG_OPTION); }
+ | CS_OPTION { add_option(CS_OPTION); }
+ | LU_OPTION { add_option(LU_OPTION); }
+ | CV_OPTION { add_option(CV_OPTION); }
+ | WB_OPTION { add_option(WB_OPTION); }
+ | WT_OPTION { add_option(WT_OPTION); }
+ | NC_OPTION { add_option(NC_OPTION); }
+ | UP_OPTION { add_option(UP_OPTION); }
+ | DOWN_OPTION { add_option(DOWN_OPTION); }
+ | BFLY_OPTION { add_option(BFLY_OPTION); }
+ | IDX_OPTION { add_option(IDX_OPTION); }
+ ;
+
+atomic_operation_spec: ATOMIC_AND { add_option(ATOMIC_AND); }
+ | ATOMIC_POPC { add_option(ATOMIC_POPC); }
+ | ATOMIC_OR { add_option(ATOMIC_OR); }
+ | ATOMIC_XOR { add_option(ATOMIC_XOR); }
+ | ATOMIC_CAS { add_option(ATOMIC_CAS); }
+ | ATOMIC_EXCH { add_option(ATOMIC_EXCH); }
+ | ATOMIC_ADD { add_option(ATOMIC_ADD); }
+ | ATOMIC_INC { add_option(ATOMIC_INC); }
+ | ATOMIC_DEC { add_option(ATOMIC_DEC); }
+ | ATOMIC_MIN { add_option(ATOMIC_MIN); }
+ | ATOMIC_MAX { add_option(ATOMIC_MAX); }
+ ;
+
+rounding_mode: floating_point_rounding_mode
+ | integer_rounding_mode;
+
+
+floating_point_rounding_mode: RN_OPTION { add_option(RN_OPTION); }
+ | RZ_OPTION { add_option(RZ_OPTION); }
+ | RM_OPTION { add_option(RM_OPTION); }
+ | RP_OPTION { add_option(RP_OPTION); }
+ ;
+
+integer_rounding_mode: RNI_OPTION { add_option(RNI_OPTION); }
+ | RZI_OPTION { add_option(RZI_OPTION); }
+ | RMI_OPTION { add_option(RMI_OPTION); }
+ | RPI_OPTION { add_option(RPI_OPTION); }
+ ;
+
+compare_spec:EQ_OPTION { add_option(EQ_OPTION); }
+ | NE_OPTION { add_option(NE_OPTION); }
+ | LT_OPTION { add_option(LT_OPTION); }
+ | LE_OPTION { add_option(LE_OPTION); }
+ | GT_OPTION { add_option(GT_OPTION); }
+ | GE_OPTION { add_option(GE_OPTION); }
+ | LO_OPTION { add_option(LO_OPTION); }
+ | LS_OPTION { add_option(LS_OPTION); }
+ | HI_OPTION { add_option(HI_OPTION); }
+ | HS_OPTION { add_option(HS_OPTION); }
+ | EQU_OPTION { add_option(EQU_OPTION); }
+ | NEU_OPTION { add_option(NEU_OPTION); }
+ | LTU_OPTION { add_option(LTU_OPTION); }
+ | LEU_OPTION { add_option(LEU_OPTION); }
+ | GTU_OPTION { add_option(GTU_OPTION); }
+ | GEU_OPTION { add_option(GEU_OPTION); }
+ | NUM_OPTION { add_option(NUM_OPTION); }
+ | NAN_OPTION { add_option(NAN_OPTION); }
+ ;
+
+prmt_spec: PRMT_F4E_MODE { add_option( PRMT_F4E_MODE); }
+ | PRMT_B4E_MODE { add_option( PRMT_B4E_MODE); }
+ | PRMT_RC8_MODE { add_option( PRMT_RC8_MODE); }
+ | PRMT_RC16_MODE{ add_option( PRMT_RC16_MODE);}
+ | PRMT_ECL_MODE { add_option( PRMT_ECL_MODE); }
+ | PRMT_ECR_MODE { add_option( PRMT_ECR_MODE); }
+ ;
+
+wmma_spec: WMMA_DIRECTIVE LAYOUT CONFIGURATION{add_space_spec(global_space,0);add_ptr_spec(global_space); add_wmma_option($1);add_wmma_option($2);add_wmma_option($3);}
+ | WMMA_DIRECTIVE LAYOUT LAYOUT CONFIGURATION{add_wmma_option($1);add_wmma_option($2);add_wmma_option($3);add_wmma_option($4);}
+ ;
+
+vp_spec: WMMA_DIRECTIVE LAYOUT CONFIGURATION{add_space_spec(global_space,0);add_ptr_spec(global_space);add_wmma_option($1);add_wmma_option($2);add_wmma_option($3);}
+ | WMMA_DIRECTIVE LAYOUT LAYOUT CONFIGURATION{add_wmma_option($1);add_wmma_option($2);add_wmma_option($3);add_wmma_option($4);}
+ ;
+
+
+
+operand_list: operand
+ | operand COMMA operand_list;
+
+operand: IDENTIFIER { add_scalar_operand( $1 ); }
+ | EXCLAMATION IDENTIFIER { add_neg_pred_operand( $2 ); }
+ | MINUS IDENTIFIER { add_scalar_operand( $2 ); change_operand_neg(); }
+ | memory_operand
+ | literal_operand
+ | builtin_operand
+ | vector_operand
+ | MINUS vector_operand { change_operand_neg(); }
+ | tex_operand
+ | IDENTIFIER PLUS INT_OPERAND { add_address_operand($1,$3); }
+ | IDENTIFIER LO_OPTION { add_scalar_operand( $1 ); change_operand_lohi(1);}
+ | MINUS IDENTIFIER LO_OPTION { add_scalar_operand( $2 ); change_operand_lohi(1); change_operand_neg();}
+ | IDENTIFIER HI_OPTION { add_scalar_operand( $1 ); change_operand_lohi(2);}
+ | MINUS IDENTIFIER HI_OPTION { add_scalar_operand( $2 ); change_operand_lohi(2); change_operand_neg();}
+ | IDENTIFIER PIPE IDENTIFIER { add_2vector_operand($1,$3); change_double_operand_type(-1);}
+ | IDENTIFIER PIPE IDENTIFIER LO_OPTION { add_2vector_operand($1,$3); change_double_operand_type(-1); change_operand_lohi(1);}
+ | IDENTIFIER PIPE IDENTIFIER HI_OPTION { add_2vector_operand($1,$3); change_double_operand_type(-1); change_operand_lohi(2);}
+ | IDENTIFIER BACKSLASH IDENTIFIER { add_2vector_operand($1,$3); change_double_operand_type(-3);}
+ | IDENTIFIER BACKSLASH IDENTIFIER LO_OPTION { add_2vector_operand($1,$3); change_double_operand_type(-3); change_operand_lohi(1);}
+ | IDENTIFIER BACKSLASH IDENTIFIER HI_OPTION { add_2vector_operand($1,$3); change_double_operand_type(-3); change_operand_lohi(2);}
+ ;
+
+vector_operand: LEFT_BRACE IDENTIFIER COMMA IDENTIFIER RIGHT_BRACE { add_2vector_operand($2,$4); }
+ | LEFT_BRACE IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER RIGHT_BRACE { add_3vector_operand($2,$4,$6); }
+ | LEFT_BRACE IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER RIGHT_BRACE { add_4vector_operand($2,$4,$6,$8); }
+ | LEFT_BRACE IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER RIGHT_BRACE { add_8vector_operand($2,$4,$6,$8,$10,$12,$14,$16); }
+ | LEFT_BRACE IDENTIFIER RIGHT_BRACE { add_1vector_operand($2); }
+ ;
+
+tex_operand: LEFT_SQUARE_BRACKET IDENTIFIER COMMA { add_scalar_operand($2); }
+ vector_operand
+ RIGHT_SQUARE_BRACKET
+ ;
+
+builtin_operand: SPECIAL_REGISTER DIMENSION_MODIFIER { add_builtin_operand($1,$2); }
+ | SPECIAL_REGISTER { add_builtin_operand($1,-1); }
+ ;
+
+memory_operand : LEFT_SQUARE_BRACKET address_expression RIGHT_SQUARE_BRACKET { add_memory_operand(); }
+ | IDENTIFIER LEFT_SQUARE_BRACKET address_expression RIGHT_SQUARE_BRACKET { add_memory_operand(); change_memory_addr_space($1); }
+ | IDENTIFIER LEFT_SQUARE_BRACKET literal_operand RIGHT_SQUARE_BRACKET { change_memory_addr_space($1); }
+ | IDENTIFIER LEFT_SQUARE_BRACKET twin_operand RIGHT_SQUARE_BRACKET { change_memory_addr_space($1); add_memory_operand();}
+ | MINUS memory_operand { change_operand_neg(); }
+ ;
+
+twin_operand : IDENTIFIER PLUS IDENTIFIER { add_double_operand($1,$3); change_double_operand_type(1); }
+ | IDENTIFIER PLUS IDENTIFIER LO_OPTION { add_double_operand($1,$3); change_double_operand_type(1); change_operand_lohi(1); }
+ | IDENTIFIER PLUS IDENTIFIER HI_OPTION { add_double_operand($1,$3); change_double_operand_type(1); change_operand_lohi(2); }
+ | IDENTIFIER PLUS EQUALS IDENTIFIER { add_double_operand($1,$4); change_double_operand_type(2); }
+ | IDENTIFIER PLUS EQUALS IDENTIFIER LO_OPTION { add_double_operand($1,$4); change_double_operand_type(2); change_operand_lohi(1); }
+ | IDENTIFIER PLUS EQUALS IDENTIFIER HI_OPTION { add_double_operand($1,$4); change_double_operand_type(2); change_operand_lohi(2); }
+ | IDENTIFIER PLUS EQUALS INT_OPERAND { add_address_operand($1,$4); change_double_operand_type(3); }
+ ;
+
+literal_operand : INT_OPERAND { add_literal_int($1); }
+ | FLOAT_OPERAND { add_literal_float($1); }
+ | DOUBLE_OPERAND { add_literal_double($1); }
+ ;
+
+address_expression: IDENTIFIER { add_address_operand($1,0); }
+ | IDENTIFIER LO_OPTION { add_address_operand($1,0); change_operand_lohi(1);}
+ | IDENTIFIER HI_OPTION { add_address_operand($1,0); change_operand_lohi(2); }
+ | IDENTIFIER PLUS INT_OPERAND { add_address_operand($1,$3); }
+ | INT_OPERAND { add_address_operand2($1); }
+ ;
+
+%%
+
+extern int ptx_lineno;
+extern const char *g_filename;
+
+void syntax_not_implemented()
+{
+ printf("Parse error (%s:%u): this syntax is not (yet) implemented:\n",g_filename,ptx_lineno);
+ ptx_error(NULL);
+ abort();
+}
diff --git a/diff.diff b/diff.diff
deleted file mode 100644
index 8ab27fe..0000000
--- a/diff.diff
+++ /dev/null
@@ -1,173 +0,0 @@
-diff --git a/libcuda/cuda_runtime_api.cc b/libcuda/cuda_runtime_api.cc
-index 5964a4d..53436d3 100644
---- a/libcuda/cuda_runtime_api.cc
-+++ b/libcuda/cuda_runtime_api.cc
-@@ -182,6 +182,8 @@ cudaError_t g_last_cudaError = cudaSuccess;
-
- extern stream_manager *g_stream_manager;
-
-+
-+
- void register_ptx_function( const char *name, function_info *impl )
- {
- // no longer need this
-@@ -1341,6 +1343,29 @@ std::string get_app_binary(){
- return self_exe_path;
- }
-
-+static int get_app_cuda_version() {
-+ int app_cuda_version = 0;
-+ char fname[1024];
-+ snprintf(fname,1024,"_app_cuda_version_XXXXXX");
-+ int fd=mkstemp(fname);
-+ close(fd);
-+ std::string app_cuda_version_command = "ldd " + get_app_binary() + " | grep libcudart.so | sed 's/.*libcudart.so.\\(.*\\) =>.*/\\1/' > " + fname;
-+ system(app_cuda_version_command.c_str());
-+ FILE * cmd = fopen(fname, "r");
-+ char buf[256];
-+ while (fgets(buf, sizeof(buf), cmd) != 0) {
-+ std::cout << buf;
-+ app_cuda_version = atoi(buf);
-+ }
-+ fclose(cmd);
-+ if ( app_cuda_version == 0 ) {
-+ printf( "Error - Cannot detect the app's CUDA version.\n" );
-+ exit(1);
-+ }
-+ return app_cuda_version;
-+}
-+
-+
- //! Call cuobjdump to extract everything (-elf -sass -ptx)
- /*!
- * This Function extract the whole PTX (for all the files) using cuobjdump
-@@ -1366,23 +1391,10 @@ void extract_code_using_cuobjdump(){
- // Running cuobjdump using dynamic link to current process
- // Needs the option '-all' to extract PTX from CDP-enabled binary
- extern bool g_cdp_enabled;
-- const int current_cuda = atoi(getenv("CUDA_VERSION_NUMBER"));
-- if ( context->get_device()->get_gpgpu()->get_config().convert_to_ptxplus() && current_cuda > 4020 ) {
-- const char* cuda_42_path = getenv("CUDA_42_INSTALL_PATH");
-- if ( NULL == cuda_42_path ) {
-- printf("You are using a new version of CUDA and PTXPLUS. You are required to have CUDA SDK 4.2 and explicitly "
-- "point to it via the environment variable $CUDA_42_INSTALL_PATH.\n\n");
-- exit(1);
-- } else {
-- command = "$CUDA_42_INSTALL_PATH/bin/cuobjdump";
-- }
-- } else {
-- command = "$CUDA_42_INSTALL_PATH/bin/cuobjdump";
-- }
- if(!g_cdp_enabled)
-- command += " -ptx -elf -sass " + app_binary + " > " + fname;
-+ command = "$CUDA_INSTALL_PATH/bin/cuobjdump -ptx -elf -sass " + app_binary + " > " + fname;
- else
-- command += " -ptx -elf -sass -all " + app_binary + " > " + fname;
-+ command = "$CUDA_INSTALL_PATH/bin/cuobjdump -ptx -elf -sass -all " + app_binary + " > " + fname;
- bool parse_output = true;
- int result = system(command.c_str());
- if(result) {
-@@ -1765,6 +1777,7 @@ void cuobjdumpParseBinary(unsigned int handle){
- //TODO: Remove temporarily files as per configurations
- }
-
-+
- void** CUDARTAPI __cudaRegisterFatBinary( void *fatCubin )
- {
- #if (CUDART_VERSION < 2010)
-@@ -1783,26 +1796,10 @@ void** CUDARTAPI __cudaRegisterFatBinary( void *fatCubin )
- // Making this a runtime variable based on the app, enables GPGPU-Sim compiled
- // with a newer version of CUDA to run apps compiled with older versions of
- // CUDA. This is especially useful for PTXPLUS execution.
-- char fname[1024];
-- snprintf(fname,1024,"_app_cuda_version_XXXXXX");
-- int fd=mkstemp(fname);
-- close(fd);
-- int app_cuda_version = 0;
-- std::string app_cuda_version_command = "ldd " + get_app_binary() + " | grep libcudart.so | sed 's/.*libcudart.so.\\(.*\\) =>.*/\\1/' > " + fname;
-- system(app_cuda_version_command.c_str());
-- FILE * cmd = fopen(fname, "r");
-- char buf[256];
-- while (fgets(buf, sizeof(buf), cmd) != 0) {
-- std::cout << buf;
-- app_cuda_version = atoi(buf);
-- }
-- fclose(cmd);
-- if ( app_cuda_version == 0 ) {
-- printf( "Error - Cannot detect the app's CUDA version.\n" );
-- exit(1);
-- }
-+ int app_cuda_version = get_app_cuda_version();
-+ assert( app_cuda_version == CUDART_VERSION / 1000 && "The app must be compiled with same major version as the simulator." );
- const char* filename;
-- if ( app_cuda_version < 6 ) {
-+#if CUDART_VERSION < 6000
- // FatBin handle from the .fatbin.c file (one of the intermediate files generated by NVCC)
- typedef struct {int m; int v; const unsigned long long* d; char* f;} __fatDeviceText __attribute__ ((aligned (8)));
- __fatDeviceText * fatDeviceText = (__fatDeviceText *) fatCubin;
-@@ -1814,9 +1811,9 @@ void** CUDARTAPI __cudaRegisterFatBinary( void *fatCubin )
- char * pfatbin = (char*) fatDeviceText->d;
- int offset = *((int*)(pfatbin+48));
- filename = (pfatbin+16+offset);
-- } else {
-+#else
- filename = "default";
-- }
-+#endif
-
- // The extracted file name is associated with a fat_cubin_handle passed
- // into cudaLaunch(). Inside cudaLaunch(), the associated file name is
-diff --git a/setup_environment b/setup_environment
-index 8bcb9aa..e5cd4fa 100644
---- a/setup_environment
-+++ b/setup_environment
-@@ -134,18 +134,26 @@ else
- echo "configured without a power model.";
- fi
-
-+export PTXAS_CUDA_INSTALL_PATH=$CUDA_INSTALL_PATH
-+echo "";
-+echo "----------------------------------------------------------------------------";
-+echo "WARNING - If you only care about PTX execution, ignore this warning. GPGPU-Sim supports PTX execution in modern CUDA."
- if [ $CUDA_VERSION_NUMBER -gt 4200 ]; then
-- echo "";
-- echo "----------------------------------------------------------------------------";
-- echo "WARNING - If you only care about PTX execution, ignore this warning. GPGPU-Sim supports PTX execution in modern CUDA."
-- echo "If you want to run PTXPLUS, download SDK 4.2 (in addition to your modern CUDA) and set \$CUDA_42_INSTALL_PATH."
-- echo "The following text describes why:";
-- echo "If you are using PTXPLUS, only sm_1x is supported and it requires that the app binaries are compiled in CUDA 4.2 or less.";
-- echo "New versions of CUDA tools have dropped parsing support for sm_1x - therefore to use PTXPLUS with a modern card configuration, you must";
-- echo "have both CUDA 4.2 and a modern CUDA installed. When running PTXPLUS under a CUDA version >= 4.2, the simulator will fail unless \$CUDA_42_INSTALL_PATH";
-- echo "has been set properly. You must set this manually.";
-- echo "----------------------------------------------------------------------------"
-+ echo "If you want to run PTXPLUS (sm_1x SASS) with a modern card configuration, the apps and simulator must be compiled with CUDA 4.2."
-+ echo "You can still run a PASCAL configuration when compiling with 4.2 by setting the \$PTXAS_CUDA_INSTALL_PATH directory environment variable."
-+else
-+ echo "If you want to run PTXPLUS (sm_1x SASS) with a modern card configuration - set the envronment variable"
-+ echo "\$PTXAS_CUDA_INSTALL_PATH to point a CUDA version compabible with your card configurations (i.e. 8+ for PASCAL, 9+ for VOLTA etc..)"
-+ echo "For example: \"export \$PTXAS_CUDA_INSTALL_PATH=/usr/local/cuda-9.1\""
- fi
-+echo "The following text describes why:";
-+echo "If you are using PTXPLUS, only sm_1x is supported and it requires that the app and simulator binaries are compiled in CUDA 4.2 or less.";
-+echo "The simulator requires it since CUDA headers desribe struct sizes in the exec which change from gen to gen.";
-+echo "The apps require 4.2 because new versions of CUDA tools have dropped parsing support for generating sm_1x";
-+echo "When running using modern config (i.e. pascal) and PTXPLUS with CUDA 4.2, the \$PTXAS_CUDA_INSTALL_PATH env variable is required to get proper register usage"
-+echo "(and hence occupancy) using a version of CUDA that knows the register usage on the real card."
-+echo "";
-+echo "----------------------------------------------------------------------------";
-
- echo "setup_environment succeeded";
-
-diff --git a/src/cuda-sim/ptx_loader.cc b/src/cuda-sim/ptx_loader.cc
-index 22f03b9..d8e04d4 100644
---- a/src/cuda-sim/ptx_loader.cc
-+++ b/src/cuda-sim/ptx_loader.cc
-@@ -339,7 +339,7 @@ void gpgpu_ptxinfo_load_from_string( const char *p_for_info, unsigned source_num
- snprintf(extra_flags,1024,"--compile-only --gpu-name=sm_%u",g_occupancy_sm_number);
- #endif
-
-- snprintf(commandline,1024,"$CUDA_INSTALL_PATH/bin/ptxas %s -v %s --output-file /dev/null 2> %s",
-+ snprintf(commandline,1024,"$PTXAS_CUDA_INSTALL_PATH/bin/ptxas %s -v %s --output-file /dev/null 2> %s",
- extra_flags, fname2, tempfile_ptxinfo);
- printf("GPGPU-Sim PTX: generating ptxinfo using \"%s\"\n", commandline);
- result = system(commandline);
diff --git a/groovy-html.nightly.success.template b/groovy-html.nightly.success.template
new file mode 100644
index 0000000..210b924
--- /dev/null
+++ b/groovy-html.nightly.success.template
@@ -0,0 +1,74 @@
+<STYLE>
+ BODY, TABLE, TD, TH, P {
+ font-family: Courier New, Verdana, Helvetica, sans serif;
+ font-size: 10px;
+ color: black;
+ }
+ .console {
+ font-family: Courier New;
+ }
+ .filesChanged {
+ width: 10%;
+ padding-left: 10px;
+ }
+ .section {
+ width: 100%;
+ border: thin black dotted;
+ }
+ .td-title-main {
+ color: white;
+ font-size: 200%;
+ padding-left: 5px;
+ font-weight: bold;
+ }
+ .td-title {
+ color: white;
+ font-size: 120%;
+ font-weight: bold;
+ padding-left: 5px;
+ text-transform: uppercase;
+ }
+ .td-title-tests {
+ font-weight: bold;
+ font-size: 120%;
+ }
+ .td-header-maven-module {
+ font-weight: bold;
+ font-size: 120%;
+ }
+ .td-maven-artifact {
+ padding-left: 5px;
+ }
+ .tr-title {
+ background-color: <%= (build.result == null || build.result.toString() == 'SUCCESS') ? '#27AE60' : build.result.toString() == 'FAILURE' ? '#E74C3C' : '#f4e242' %>;
+ }
+ .test {
+ padding-left: 20px;
+ }
+ .test-fixed {
+ color: #27AE60;
+ }
+ .test-failed {
+ color: #E74C3C;
+ }
+</STYLE>
+<BODY>
+
+<%
+ import hudson.model.*
+
+ def JOB_NAME= build.getEnvVars()["JOB_NAME"];
+ def BUILD_NUMBER= build.getEnvVars()["BUILD_NUMBER"];
+ def BUILD_URL= build.getEnvVars()["BUILD_URL"];
+%>
+
+See ${BUILD_URL} for full build detials.
+
+<pre>Statistics changes since last commit:
+<pre> https://engineering.purdue.edu/tgrogers/gpgpu-sim-plots/jenkins/${JOB_NAME}/${BUILD_NUMBER}/
+<pre> Correlation:
+<pre> 9.1:
+<pre> https://engineering.purdue.edu/tgrogers/gpgpu-sim-plots/jenkins/${JOB_NAME}/${BUILD_NUMBER}/titanv-cycles.cuda-9.1.nightly.html
+<pre> https://engineering.purdue.edu/tgrogers/gpgpu-sim-plots/jenkins/${JOB_NAME}/${BUILD_NUMBER}/titanv-cycles.cuda-9.1.nightly.apps.txt
+<pre> Correlation also posted to: https://engineering.purdue.edu/tgrogers/group/correlator.html
+</BODY>
diff --git a/groovy-html.success.template b/groovy-html.success.template
new file mode 100644
index 0000000..974cc61
--- /dev/null
+++ b/groovy-html.success.template
@@ -0,0 +1,77 @@
+<STYLE>
+ BODY, TABLE, TD, TH, P {
+ font-family: Courier New, Verdana, Helvetica, sans serif;
+ font-size: 10px;
+ color: black;
+ }
+ .console {
+ font-family: Courier New;
+ }
+ .filesChanged {
+ width: 10%;
+ padding-left: 10px;
+ }
+ .section {
+ width: 100%;
+ border: thin black dotted;
+ }
+ .td-title-main {
+ color: white;
+ font-size: 200%;
+ padding-left: 5px;
+ font-weight: bold;
+ }
+ .td-title {
+ color: white;
+ font-size: 120%;
+ font-weight: bold;
+ padding-left: 5px;
+ text-transform: uppercase;
+ }
+ .td-title-tests {
+ font-weight: bold;
+ font-size: 120%;
+ }
+ .td-header-maven-module {
+ font-weight: bold;
+ font-size: 120%;
+ }
+ .td-maven-artifact {
+ padding-left: 5px;
+ }
+ .tr-title {
+ background-color: <%= (build.result == null || build.result.toString() == 'SUCCESS') ? '#27AE60' : build.result.toString() == 'FAILURE' ? '#E74C3C' : '#f4e242' %>;
+ }
+ .test {
+ padding-left: 20px;
+ }
+ .test-fixed {
+ color: #27AE60;
+ }
+ .test-failed {
+ color: #E74C3C;
+ }
+</STYLE>
+<BODY>
+
+<%
+ import hudson.model.*
+
+ def JOB_NAME= build.getEnvVars()["JOB_NAME"];
+ def BUILD_NUMBER= build.getEnvVars()["BUILD_NUMBER"];
+ def BUILD_URL= build.getEnvVars()["BUILD_URL"];
+%>
+
+See ${BUILD_URL} for full build detials.
+
+<pre>Statistics changes since last commit:
+<pre> https://engineering.purdue.edu/tgrogers/gpgpu-sim-plots/jenkins/${JOB_NAME}/${BUILD_NUMBER}/
+<pre> Correlation:
+<pre> 4.2:
+<pre> https://engineering.purdue.edu/tgrogers/gpgpu-sim-plots/jenkins/${JOB_NAME}/${BUILD_NUMBER}/titanv-cycles.cuda-4.2.html
+<pre> https://engineering.purdue.edu/tgrogers/gpgpu-sim-plots/jenkins/${JOB_NAME}/${BUILD_NUMBER}/titanv-cycles.cuda-4.2.apps.txt
+<pre> 10.1:
+<pre> https://engineering.purdue.edu/tgrogers/gpgpu-sim-plots/jenkins/${JOB_NAME}/${BUILD_NUMBER}/titanv-cycles.cuda-10.1.html
+<pre> https://engineering.purdue.edu/tgrogers/gpgpu-sim-plots/jenkins/${JOB_NAME}/${BUILD_NUMBER}/titanv-cycles.cuda-10.1.apps.txt
+<pre> Correlation also posted to: https://engineering.purdue.edu/tgrogers/group/correlator.html
+</BODY>
diff --git a/libcuda/Makefile b/libcuda/Makefile
index 13932e2..c8ff2e3 100644
--- a/libcuda/Makefile
+++ b/libcuda/Makefile
@@ -111,10 +111,10 @@ $(OUTPUT_DIR)/%.o: %.cc
$(CPP) $(CXXFLAGS) -I./ -I$(OUTPUT_DIR) -I$(CUDA_INSTALL_PATH)/include -c $< -o $@
$(OUTPUT_DIR)/%.o: %.c
- $(CC) $(CCFLAGS) -I./ -I$(OUTPUT_DIR) -I$(CUDA_INSTALL_PATH)/include -c $< -o $@
+ $(CPP) $(CCFLAGS) -I./ -I$(OUTPUT_DIR) -I$(CUDA_INSTALL_PATH)/include -c $< -o $@
$(OUTPUT_DIR)/%.o: $(OUTPUT_DIR)/%.c
- $(CC) $(CCFLAGS) -I./ -I$(OUTPUT_DIR) -I$(CUDA_INSTALL_PATH)/include -c $< -o $@
+ $(CPP) $(CCFLAGS) -I./ -I$(OUTPUT_DIR) -I$(CUDA_INSTALL_PATH)/include -c $< -o $@
$(OUTPUT_DIR)/cuobjdump_parser.c: cuobjdump.y
$(YACC) $(YFLAGS) -p cuobjdump_ -o$@ $< --file-prefix=$(OUTPUT_DIR)/cuobjdump
diff --git a/libcuda/cuda_api_object.h b/libcuda/cuda_api_object.h
new file mode 100644
index 0000000..51416f2
--- /dev/null
+++ b/libcuda/cuda_api_object.h
@@ -0,0 +1,213 @@
+#ifndef __cuda_api_object_h__
+#define __cuda_api_object_h__
+
+#include <list>
+#include <map>
+#include <set>
+#include <string>
+
+#include "builtin_types.h"
+
+#include "../src/gpgpu-sim/gpu-sim.h"
+#include "../src/cuda-sim/ptx_ir.h"
+#include "../src/abstract_hardware_model.h"
+#include "cuobjdump.h"
+
+typedef std::list<gpgpu_ptx_sim_arg> gpgpu_ptx_sim_arg_list_t;
+
+#ifndef OPENGL_SUPPORT
+typedef unsigned long GLuint;
+#endif
+
+struct glbmap_entry {
+ GLuint m_bufferObj;
+ void *m_devPtr;
+ size_t m_size;
+ struct glbmap_entry *m_next;
+};
+
+typedef struct glbmap_entry glbmap_entry_t;
+
+struct _cuda_device_id {
+ _cuda_device_id(gpgpu_sim* gpu) {m_id = 0; m_next = NULL; m_gpgpu=gpu;}
+ struct _cuda_device_id *next() { return m_next; }
+ unsigned num_shader() const { return m_gpgpu->get_config().num_shader(); }
+ int num_devices() const {
+ if( m_next == NULL ) return 1;
+ else return 1 + m_next->num_devices();
+ }
+ struct _cuda_device_id *get_device( unsigned n )
+ {
+ assert( n < (unsigned)num_devices() );
+ struct _cuda_device_id *p=this;
+ for(unsigned i=0; i<n; i++)
+ p = p->m_next;
+ return p;
+ }
+ const struct cudaDeviceProp *get_prop() const
+ {
+ return m_gpgpu->get_prop();
+ }
+ unsigned get_id() const { return m_id; }
+
+ gpgpu_sim *get_gpgpu() { return m_gpgpu; }
+private:
+ unsigned m_id;
+ class gpgpu_sim *m_gpgpu;
+ struct _cuda_device_id *m_next;
+};
+
+struct CUctx_st {
+ CUctx_st( _cuda_device_id *gpu )
+ {
+ m_gpu = gpu;
+ m_binary_info.cmem = 0;
+ m_binary_info.gmem = 0;
+ no_of_ptx=0;
+ }
+
+ _cuda_device_id *get_device() { return m_gpu; }
+
+ void add_binary( symbol_table *symtab, unsigned fat_cubin_handle )
+ {
+ m_code[fat_cubin_handle] = symtab;
+ m_last_fat_cubin_handle = fat_cubin_handle;
+ }
+
+ void add_ptxinfo( const char *deviceFun, const struct gpgpu_ptx_sim_info &info )
+ {
+ symbol *s = m_code[m_last_fat_cubin_handle]->lookup(deviceFun);
+ assert( s != NULL );
+ function_info *f = s->get_pc();
+ assert( f != NULL );
+ f->set_kernel_info(info);
+ }
+
+ void add_ptxinfo( const struct gpgpu_ptx_sim_info &info )
+ {
+ m_binary_info = info;
+ }
+
+ void register_function( unsigned fat_cubin_handle, const char *hostFun, const char *deviceFun )
+ {
+ if( m_code.find(fat_cubin_handle) != m_code.end() ) {
+ symbol *s = m_code[fat_cubin_handle]->lookup(deviceFun);
+ if(s != NULL) {
+ function_info *f = s->get_pc();
+ assert( f != NULL );
+ m_kernel_lookup[hostFun] = f;
+ }
+ else {
+ printf("Warning: cannot find deviceFun %s\n", deviceFun);
+ m_kernel_lookup[hostFun] = NULL;
+ }
+ // assert( s != NULL );
+ // function_info *f = s->get_pc();
+ // assert( f != NULL );
+ // m_kernel_lookup[hostFun] = f;
+ } else {
+ m_kernel_lookup[hostFun] = NULL;
+ }
+ }
+
+ void register_hostFun_function( const char*hostFun, function_info* f){
+ m_kernel_lookup[hostFun] = f;
+ }
+
+ function_info *get_kernel(const char *hostFun)
+ {
+ std::map<const void*,function_info*>::iterator i=m_kernel_lookup.find(hostFun);
+ assert( i != m_kernel_lookup.end() );
+ return i->second;
+ }
+
+ int no_of_ptx;
+
+private:
+ _cuda_device_id *m_gpu; // selected gpu
+ std::map<unsigned,symbol_table*> m_code; // fat binary handle => global symbol table
+ unsigned m_last_fat_cubin_handle;
+ std::map<const void*,function_info*> m_kernel_lookup; // unique id (CUDA app function address) => kernel entry point
+ struct gpgpu_ptx_sim_info m_binary_info;
+
+};
+
+class kernel_config {
+public:
+ kernel_config( dim3 GridDim, dim3 BlockDim, size_t sharedMem, struct CUstream_st *stream )
+ {
+ m_GridDim=GridDim;
+ m_BlockDim=BlockDim;
+ m_sharedMem=sharedMem;
+ m_stream = stream;
+ }
+ kernel_config()
+ {
+ m_GridDim=dim3(-1,-1,-1);
+ m_BlockDim=dim3(-1,-1,-1);
+ m_sharedMem=0;
+ m_stream =NULL;
+ }
+ void set_arg( const void *arg, size_t size, size_t offset )
+ {
+ m_args.push_front( gpgpu_ptx_sim_arg(arg,size,offset) );
+ }
+ dim3 grid_dim() const { return m_GridDim; }
+ dim3 block_dim() const { return m_BlockDim; }
+ void set_grid_dim(dim3 *d) { m_GridDim = *d; }
+ void set_block_dim(dim3 *d) { m_BlockDim = *d; }
+ gpgpu_ptx_sim_arg_list_t get_args() { return m_args; }
+ struct CUstream_st *get_stream() { return m_stream; }
+
+private:
+ dim3 m_GridDim;
+ dim3 m_BlockDim;
+ size_t m_sharedMem;
+ struct CUstream_st *m_stream;
+ gpgpu_ptx_sim_arg_list_t m_args;
+};
+
+class cuda_runtime_api {
+ public:
+ cuda_runtime_api( gpgpu_context* ctx ) {
+ g_glbmap = NULL;
+ g_active_device = 0; //active gpu that runs the code
+ gpgpu_ctx = ctx;
+ }
+ // global list
+ std::list<cuobjdumpSection*> cuobjdumpSectionList;
+ std::list<cuobjdumpSection*> libSectionList;
+ std::list<kernel_config> g_cuda_launch_stack;
+ std::map<int, bool>fatbin_registered;
+ std::map<int, std::string> fatbinmap;
+ std::map<std::string, symbol_table*> name_symtab;
+ std::map<unsigned long long, size_t> g_mallocPtr_Size;
+ //maps sm version number to set of filenames
+ std::map<unsigned, std::set<std::string> > version_filename;
+ std::map<void *,void **> pinned_memory; //support for pinned memories added
+ std::map<void *, size_t> pinned_memory_size;
+ glbmap_entry_t* g_glbmap;
+ int g_active_device; //active gpu that runs the code
+ // backward pointer
+ class gpgpu_context* gpgpu_ctx;
+ // member function list
+ void cuobjdumpInit();
+ void extract_code_using_cuobjdump();
+ void extract_ptx_files_using_cuobjdump(CUctx_st *context);
+ std::list<cuobjdumpSection*> pruneSectionList(CUctx_st *context);
+ std::list<cuobjdumpSection*> mergeMatchingSections(std::string identifier);
+ std::list<cuobjdumpSection*> mergeSections();
+ cuobjdumpELFSection* findELFSection(const std::string identifier);
+ cuobjdumpPTXSection* findPTXSection(const std::string identifier);
+ cuobjdumpPTXSection* findPTXSectionInList(std::list<cuobjdumpSection*> &sectionlist, const std::string identifier);
+ void cuobjdumpRegisterFatBinary(unsigned int handle, const char* filename, CUctx_st *context);
+ kernel_info_t *gpgpu_cuda_ptx_sim_init_grid( const char *kernel_key,
+ gpgpu_ptx_sim_arg_list_t args,
+ struct dim3 gridDim,
+ struct dim3 blockDim,
+ struct CUctx_st* context );
+ int load_static_globals( symbol_table *symtab, unsigned min_gaddr, unsigned max_gaddr, gpgpu_t *gpu );
+ int load_constants( symbol_table *symtab, addr_t min_gaddr, gpgpu_t *gpu );
+
+};
+#endif /* __cuda_api_object_h__ */
diff --git a/libcuda/cuda_runtime_api.cc b/libcuda/cuda_runtime_api.cc
index 45511d4..9d685e6 100644
--- a/libcuda/cuda_runtime_api.cc
+++ b/libcuda/cuda_runtime_api.cc
@@ -131,6 +131,8 @@
#if (CUDART_VERSION < 8000)
#include "__cudaFatFormat.h"
#endif
+#include "gpgpu_context.h"
+#include "cuda_api_object.h"
#include "../src/gpgpu-sim/gpu-sim.h"
#include "../src/cuda-sim/ptx_loader.h"
#include "../src/cuda-sim/cuda-sim.h"
@@ -147,25 +149,10 @@
#include <mach-o/dyld.h>
#endif
-std::map<void *,void **> pinned_memory; //support for pinned memories added
-std::map<void *, size_t> pinned_memory_size;
-std::map<unsigned long long, size_t> g_mallocPtr_Size;
-int no_of_ptx=0;
-//maps sm version number to set of filenames
-std::map<unsigned, std::set<std::string> > version_filename;
extern void synchronize();
extern void exit_simulation();
-static int load_static_globals( symbol_table *symtab, unsigned min_gaddr, unsigned max_gaddr, gpgpu_t *gpu );
-static int load_constants( symbol_table *symtab, addr_t min_gaddr, gpgpu_t *gpu );
-
-static kernel_info_t *gpgpu_cuda_ptx_sim_init_grid( const char *kernel_key,
- gpgpu_ptx_sim_arg_list_t args,
- struct dim3 gridDim,
- struct dim3 blockDim,
- struct CUctx_st* context );
-
/*DEVICE_BUILTIN*/
struct cudaArray
{
@@ -189,7 +176,7 @@ struct cudaArray
cudaError_t g_last_cudaError = cudaSuccess;
-extern stream_manager *g_stream_manager;
+//extern stream_manager *g_stream_manager();
void register_ptx_function( const char *name, function_info *impl )
{
@@ -210,145 +197,10 @@ void register_ptx_function( const char *name, function_info *impl )
# endif
#endif
-struct _cuda_device_id {
- _cuda_device_id(gpgpu_sim* gpu) {m_id = 0; m_next = NULL; m_gpgpu=gpu;}
- struct _cuda_device_id *next() { return m_next; }
- unsigned num_shader() const { return m_gpgpu->get_config().num_shader(); }
- int num_devices() const {
- if( m_next == NULL ) return 1;
- else return 1 + m_next->num_devices();
- }
- struct _cuda_device_id *get_device( unsigned n )
- {
- assert( n < (unsigned)num_devices() );
- struct _cuda_device_id *p=this;
- for(unsigned i=0; i<n; i++)
- p = p->m_next;
- return p;
- }
- const struct cudaDeviceProp *get_prop() const
- {
- return m_gpgpu->get_prop();
- }
- unsigned get_id() const { return m_id; }
-
- gpgpu_sim *get_gpgpu() { return m_gpgpu; }
-private:
- unsigned m_id;
- class gpgpu_sim *m_gpgpu;
- struct _cuda_device_id *m_next;
-};
-
-struct CUctx_st {
- CUctx_st( _cuda_device_id *gpu )
- {
- m_gpu = gpu;
- m_binary_info.cmem = 0;
- m_binary_info.gmem = 0;
- }
-
- _cuda_device_id *get_device() { return m_gpu; }
-
- void add_binary( symbol_table *symtab, unsigned fat_cubin_handle )
- {
- m_code[fat_cubin_handle] = symtab;
- m_last_fat_cubin_handle = fat_cubin_handle;
- }
-
- void add_ptxinfo( const char *deviceFun, const struct gpgpu_ptx_sim_info &info )
- {
- symbol *s = m_code[m_last_fat_cubin_handle]->lookup(deviceFun);
- assert( s != NULL );
- function_info *f = s->get_pc();
- assert( f != NULL );
- f->set_kernel_info(info);
- }
-
- void add_ptxinfo( const struct gpgpu_ptx_sim_info &info )
- {
- m_binary_info = info;
- }
-
- void register_function( unsigned fat_cubin_handle, const char *hostFun, const char *deviceFun )
- {
- if( m_code.find(fat_cubin_handle) != m_code.end() ) {
- symbol *s = m_code[fat_cubin_handle]->lookup(deviceFun);
- if(s != NULL) {
- function_info *f = s->get_pc();
- assert( f != NULL );
- m_kernel_lookup[hostFun] = f;
- }
- else {
- printf("Warning: cannot find deviceFun %s\n", deviceFun);
- m_kernel_lookup[hostFun] = NULL;
- }
- // assert( s != NULL );
- // function_info *f = s->get_pc();
- // assert( f != NULL );
- // m_kernel_lookup[hostFun] = f;
- } else {
- m_kernel_lookup[hostFun] = NULL;
- }
- }
-
- void register_hostFun_function( const char*hostFun, function_info* f){
- m_kernel_lookup[hostFun] = f;
- }
-
- function_info *get_kernel(const char *hostFun)
- {
- std::map<const void*,function_info*>::iterator i=m_kernel_lookup.find(hostFun);
- assert( i != m_kernel_lookup.end() );
- return i->second;
- }
-
-private:
- _cuda_device_id *m_gpu; // selected gpu
- std::map<unsigned,symbol_table*> m_code; // fat binary handle => global symbol table
- unsigned m_last_fat_cubin_handle;
- std::map<const void*,function_info*> m_kernel_lookup; // unique id (CUDA app function address) => kernel entry point
- struct gpgpu_ptx_sim_info m_binary_info;
-
-};
-
-class kernel_config {
-public:
- kernel_config( dim3 GridDim, dim3 BlockDim, size_t sharedMem, struct CUstream_st *stream )
- {
- m_GridDim=GridDim;
- m_BlockDim=BlockDim;
- m_sharedMem=sharedMem;
- m_stream = stream;
- }
- kernel_config()
- {
- m_GridDim=dim3(-1,-1,-1);
- m_BlockDim=dim3(-1,-1,-1);
- m_sharedMem=0;
- m_stream =NULL;
- }
- void set_arg( const void *arg, size_t size, size_t offset )
- {
- m_args.push_front( gpgpu_ptx_sim_arg(arg,size,offset) );
- }
- dim3 grid_dim() const { return m_GridDim; }
- dim3 block_dim() const { return m_BlockDim; }
- void set_grid_dim(dim3 *d) { m_GridDim = *d; }
- void set_block_dim(dim3 *d) { m_BlockDim = *d; }
- gpgpu_ptx_sim_arg_list_t get_args() { return m_args; }
- struct CUstream_st *get_stream() { return m_stream; }
-
-private:
- dim3 m_GridDim;
- dim3 m_BlockDim;
- size_t m_sharedMem;
- struct CUstream_st *m_stream;
- gpgpu_ptx_sim_arg_list_t m_args;
-};
-
-struct _cuda_device_id *GPGPUSim_Init()
+struct _cuda_device_id *gpgpu_context::GPGPUSim_Init()
{
- static _cuda_device_id *the_device = NULL;
+ //static _cuda_device_id *the_device = NULL;
+ _cuda_device_id *the_device = GPGPUsim_ctx_ptr()->the_cude_device;
if( !the_device ) {
gpgpu_sim *the_gpu = gpgpu_ptx_sim_init_perf();
@@ -393,7 +245,8 @@ struct _cuda_device_id *GPGPUSim_Init()
prop->maxThreadsPerMultiProcessor = the_gpu->threads_per_core();
#endif
the_gpu->set_prop(prop);
- the_device = new _cuda_device_id(the_gpu);
+ GPGPUsim_ctx_ptr()->the_cude_device = new _cuda_device_id(the_gpu);
+ the_device = GPGPUsim_ctx_ptr()->the_cude_device;
}
start_sim_thread(1);
return the_device;
@@ -401,15 +254,27 @@ struct _cuda_device_id *GPGPUSim_Init()
static CUctx_st* GPGPUSim_Context()
{
- static CUctx_st *the_context = NULL;
+ //static CUctx_st *the_context = NULL;
+ gpgpu_context *cur_ctx = GPGPU_Context();
+ CUctx_st *the_context = GPGPUsim_ctx_ptr()->the_context;
if( the_context == NULL ) {
- _cuda_device_id *the_gpu = GPGPUSim_Init();
- the_context = new CUctx_st(the_gpu);
+ _cuda_device_id *the_gpu = cur_ctx->GPGPUSim_Init();
+ GPGPUsim_ctx_ptr()->the_context = new CUctx_st(the_gpu);
+ the_context = GPGPUsim_ctx_ptr()->the_context;
}
return the_context;
}
- void ptxinfo_addinfo()
+gpgpu_context* GPGPU_Context()
+{
+ static gpgpu_context *gpgpu_ctx = NULL;
+ if( gpgpu_ctx == NULL ) {
+ gpgpu_ctx = new gpgpu_context();
+ }
+ return gpgpu_ctx;
+}
+
+ void ptxinfo_data::ptxinfo_addinfo()
{
if(!get_ptxinfo_kname()){
/* This info is not per kernel (since CUDA 5.0 some info (e.g. gmem, and cmem) is added at the beginning for the whole binary ) */
@@ -480,29 +345,618 @@ typedef std::map<unsigned,CUevent_st*> event_tracker_t;
int CUevent_st::m_next_event_uid;
event_tracker_t g_timer_events;
-int g_active_device = 0; //active gpu that runs the code
-std::list<kernel_config> g_cuda_launch_stack;
-/*******************************************************************************
- * *
- * *
- * *
- *******************************************************************************/
+extern int cuobjdump_lex_init(yyscan_t* scanner);
+extern void cuobjdump_set_in (FILE * _in_str ,yyscan_t yyscanner );
+extern int cuobjdump_parse(yyscan_t scanner, struct cuobjdump_parser* parser, std::list<cuobjdumpSection*> &cuobjdumpSectionList);
+extern int cuobjdump_lex_destroy(yyscan_t scanner);
+
+enum cuobjdumpSectionType {
+ PTXSECTION=0,
+ ELFSECTION
+};
+
+
+// sectiontype: 0 for ptx, 1 for elf
+void addCuobjdumpSection(int sectiontype, std::list<cuobjdumpSection*> &cuobjdumpSectionList){
+ if (sectiontype)
+ cuobjdumpSectionList.push_front(new cuobjdumpELFSection());
+ else
+ cuobjdumpSectionList.push_front(new cuobjdumpPTXSection());
+ printf("## Adding new section %s\n", sectiontype?"ELF":"PTX");
+}
+
+void setCuobjdumparch(const char* arch, std::list<cuobjdumpSection*> &cuobjdumpSectionList){
+ unsigned archnum;
+ sscanf(arch, "sm_%u", &archnum);
+ assert (archnum && "cannot have sm_0");
+ printf("Adding arch: %s\n", arch);
+ cuobjdumpSectionList.front()->setArch(archnum);
+}
+
+void setCuobjdumpidentifier(const char* identifier, std::list<cuobjdumpSection*> &cuobjdumpSectionList){
+ printf("Adding identifier: %s\n", identifier);
+ cuobjdumpSectionList.front()->setIdentifier(identifier);
+}
+
+void setCuobjdumpptxfilename(const char* filename, std::list<cuobjdumpSection*> &cuobjdumpSectionList){
+ printf("Adding ptx filename: %s\n", filename);
+ cuobjdumpSection* x = cuobjdumpSectionList.front();
+ if (dynamic_cast<cuobjdumpPTXSection*>(x) == NULL){
+ assert (0 && "You shouldn't be trying to add a ptxfilename to an elf section");
+ }
+ (dynamic_cast<cuobjdumpPTXSection*>(x))->setPTXfilename(filename);
+}
+
+void setCuobjdumpelffilename(const char* filename, std::list<cuobjdumpSection*> &cuobjdumpSectionList){
+ if (dynamic_cast<cuobjdumpELFSection*>(cuobjdumpSectionList.front()) == NULL){
+ assert (0 && "You shouldn't be trying to add a elffilename to an ptx section");
+ }
+ (dynamic_cast<cuobjdumpELFSection*>(cuobjdumpSectionList.front()))->setELFfilename(filename);
+}
+
+void setCuobjdumpsassfilename(const char* filename, std::list<cuobjdumpSection*> &cuobjdumpSectionList){
+ if (dynamic_cast<cuobjdumpELFSection*>(cuobjdumpSectionList.front()) == NULL){
+ assert (0 && "You shouldn't be trying to add a sassfilename to an ptx section");
+ }
+ (dynamic_cast<cuobjdumpELFSection*>(cuobjdumpSectionList.front()))->setSASSfilename(filename);
+}
+
+//! Return the executable file of the process containing the PTX/SASS code
+//!
+//! This Function returns the executable file ran by the process. This
+//! executable is supposed to contain the PTX/SASS code. It provides workaround
+//! for processes running on valgrind by dereferencing /proc/<pid>/exe within the
+//! GPGPU-Sim process before calling cuobjdump to extract PTX/SASS. This is
+//! needed because valgrind uses x86 emulation to detect memory leak. Other
+//! processes (e.g. cuobjdump) reading /proc/<pid>/exe will see the emulator
+//! executable instead of the application binary.
+//!
+std::string get_app_binary(){
+ char self_exe_path[1025];
+#ifdef __APPLE__
+ uint32_t size = sizeof(self_exe_path);
+ if( _NSGetExecutablePath(self_exe_path,&size) != 0 ) {
+ printf("GPGPU-Sim ** ERROR: _NSGetExecutablePath input buffer too small\n");
+ exit(1);
+ }
+#else
+ std::stringstream exec_link;
+ exec_link << "/proc/self/exe";
+
+ ssize_t path_length = readlink(exec_link.str().c_str(), self_exe_path, 1024);
+ assert(path_length != -1);
+ self_exe_path[path_length] = '\0';
+#endif
+
+ printf("self exe links to: %s\n", self_exe_path);
+ return self_exe_path;
+}
+
+//above func gives abs path whereas this give just the name of application.
+char* get_app_binary_name(std::string abs_path){
+ char *self_exe_path;
+#ifdef __APPLE__
+ //TODO: get apple device and check the result.
+ printf("WARNING: not tested for Apple-mac devices \n");
+ abort();
+#else
+ char* buf = strdup(abs_path.c_str());
+ char *token = strtok(buf, "/");
+ while(token !=NULL){
+ self_exe_path = token;
+ token = strtok(NULL,"/");
+ }
+#endif
+ self_exe_path = strtok(self_exe_path, ".");
+ printf("self exe links to: %s\n", self_exe_path);
+ return self_exe_path;
+}
+
+static int get_app_cuda_version() {
+ int app_cuda_version = 0;
+ char fname[1024];
+ snprintf(fname,1024,"_app_cuda_version_XXXXXX");
+ int fd=mkstemp(fname);
+ close(fd);
+ std::string app_cuda_version_command = "ldd " + get_app_binary() + " | grep libcudart.so | sed 's/.*libcudart.so.\\(.*\\) =>.*/\\1/' > " + fname;
+ system(app_cuda_version_command.c_str());
+ FILE * cmd = fopen(fname, "r");
+ char buf[256];
+ while (fgets(buf, sizeof(buf), cmd) != 0) {
+ std::cout << buf;
+ app_cuda_version = atoi(buf);
+ }
+ fclose(cmd);
+ if ( app_cuda_version == 0 ) {
+ printf( "Error - Cannot detect the app's CUDA version.\n" );
+ exit(1);
+ }
+ return app_cuda_version;
+}
+
+//! Keep track of the association between filename and cubin handle
+void cuda_runtime_api::cuobjdumpRegisterFatBinary(unsigned int handle, const char* filename, CUctx_st *context){
+ fatbinmap[handle] = filename;
+}
+
-extern "C" {
/*******************************************************************************
- * *
- * *
- * *
+ * Add internal cuda runtime API call to accept gpgpu_context *
*******************************************************************************/
-cudaError_t cudaPeekAtLastError(void)
+cudaError_t cudaSetDeviceInternal(int device, gpgpu_context* gpgpu_ctx = NULL)
{
- return g_last_cudaError;
+ gpgpu_context *ctx;
+ if (gpgpu_ctx){
+ ctx = gpgpu_ctx;
+ } else {
+ ctx = GPGPU_Context();
+ }
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ //set the active device to run cuda
+ if ( device <= ctx->GPGPUSim_Init()->num_devices() ) {
+ ctx->api->g_active_device = device;
+ return g_last_cudaError = cudaSuccess;
+ } else {
+ return g_last_cudaError = cudaErrorInvalidDevice;
+ }
}
-__host__ cudaError_t CUDARTAPI cudaMalloc(void **devPtr, size_t size)
+cudaError_t cudaGetDeviceInternal(int *device, gpgpu_context* gpgpu_ctx = NULL)
+{
+ gpgpu_context *ctx;
+ if (gpgpu_ctx){
+ ctx = gpgpu_ctx;
+ } else {
+ ctx = GPGPU_Context();
+ }
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ *device = ctx->api->g_active_device;
+ return g_last_cudaError = cudaSuccess;
+}
+
+__host__ cudaError_t CUDARTAPI cudaDeviceGetLimitInternal( size_t* pValue, cudaLimit limit, gpgpu_context* gpgpu_ctx = NULL )
+{
+ gpgpu_context *ctx;
+ if (gpgpu_ctx){
+ ctx = gpgpu_ctx;
+ } else {
+ ctx = GPGPU_Context();
+ }
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ _cuda_device_id *dev = ctx->GPGPUSim_Init();
+ const struct cudaDeviceProp *prop = dev->get_prop();
+ const gpgpu_sim_config& config=dev->get_gpgpu()->get_config();
+ switch(limit) {
+ case 0: // cudaLimitStackSize
+ *pValue=config.stack_limit();
+ break;
+ case 2: // cudaLimitMallocHeapSize
+ *pValue=config.heap_limit();
+ break;
+#if (CUDART_VERSION > 5050)
+ case 3: // cudaLimitDevRuntimeSyncDepth
+ if(prop->major > 2){
+ *pValue=config.sync_depth_limit();
+ break;
+ }
+ else{
+ printf("ERROR:Limit %s is not supported on this architecture \n",limit);
+ abort();
+ }
+ case 4: // cudaLimitDevRuntimePendingLaunchCount
+ if(prop->major > 2){
+ *pValue=config.pending_launch_count_limit();
+ break;
+ }
+ else{
+ printf("ERROR:Limit %s is not supported on this architecture \n",limit);
+ abort();
+ }
+#endif
+ default:
+ printf("ERROR:Limit %s unimplemented \n",limit);
+ abort();
+ }
+ return g_last_cudaError = cudaSuccess;
+
+}
+
+
+void** cudaRegisterFatBinaryInternal( void *fatCubin, gpgpu_context* gpgpu_ctx = NULL)
{
+ gpgpu_context *ctx;
+ if (gpgpu_ctx){
+ ctx = gpgpu_ctx;
+ } else {
+ ctx = GPGPU_Context();
+ }
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+#if (CUDART_VERSION < 2010)
+ printf("GPGPU-Sim PTX: ERROR ** this version of GPGPU-Sim requires CUDA 2.1 or higher\n");
+ exit(1);
+#endif
+ CUctx_st *context = GPGPUSim_Context();
+ static unsigned next_fat_bin_handle = 1;
+ if(context->get_device()->get_gpgpu()->get_config().use_cuobjdump()) {
+ // The following workaround has only been verified on 64-bit systems.
+ if (sizeof(void*) == 4)
+ printf("GPGPU-Sim PTX: FatBin file name extraction has not been tested on 32-bit system.\n");
+
+ // This code will get the CUDA version the app was compiled with.
+ // We need this to determine how to handle the parsing of the binary.
+ // Making this a runtime variable based on the app, enables GPGPU-Sim compiled
+ // with a newer version of CUDA to run apps compiled with older versions of
+ // CUDA. This is especially useful for PTXPLUS execution.
+ //Skip cuda version check for pytorch application
+ std::string app_binary_path = get_app_binary();
+ int pos = app_binary_path.find("python");
+ if (pos==std::string::npos){
+ // Not pytorch app : checking cuda version
+ int app_cuda_version = get_app_cuda_version();
+ assert( app_cuda_version == CUDART_VERSION / 1000 && "The app must be compiled with same major version as the simulator." );
+ }
+
+ //int app_cuda_version = get_app_cuda_version();
+ //assert( app_cuda_version == CUDART_VERSION / 1000 && "The app must be compiled with same major version as the simulator." );
+ const char* filename;
+#if CUDART_VERSION < 6000
+ // FatBin handle from the .fatbin.c file (one of the intermediate files generated by NVCC)
+ typedef struct {int m; int v; const unsigned long long* d; char* f;} __fatDeviceText __attribute__ ((aligned (8)));
+ __fatDeviceText * fatDeviceText = (__fatDeviceText *) fatCubin;
+
+ // Extract the source code file name that generate the given FatBin.
+ // - Obtains the pointer to the actual fatbin structure from the FatBin handle (fatCubin).
+ // - An integer inside the fatbin structure contains the relative offset to the source code file name.
+ // - This offset differs among different CUDA and GCC versions.
+ char * pfatbin = (char*) fatDeviceText->d;
+ int offset = *((int*)(pfatbin+48));
+ filename = (pfatbin+16+offset);
+#else
+ filename = "default";
+#endif
+
+ // The extracted file name is associated with a fat_cubin_handle passed
+ // into cudaLaunch(). Inside cudaLaunch(), the associated file name is
+ // used to find the PTX/SASS section from cuobjdump, which contains the
+ // PTX/SASS code for the launched kernel function.
+ // This allows us to work around the fact that cuobjdump only outputs the
+ // file name associated with each section.
+ unsigned long long fat_cubin_handle = next_fat_bin_handle;
+ next_fat_bin_handle++;
+ printf("GPGPU-Sim PTX: __cudaRegisterFatBinary, fat_cubin_handle = %llu, filename=%s\n", fat_cubin_handle, filename);
+ /*!
+ * This function extracts all data from all files in first call
+ * then for next calls, only returns the appropriate number
+ */
+ assert(fat_cubin_handle >= 1);
+ if (fat_cubin_handle==1) ctx->api->cuobjdumpInit();
+ ctx->api->cuobjdumpRegisterFatBinary(fat_cubin_handle, filename, context);
+
+ return (void**)fat_cubin_handle;
+ }
+#if (CUDART_VERSION < 8000)
+ else {
+ static unsigned source_num=1;
+ unsigned long long fat_cubin_handle = next_fat_bin_handle++;
+ __cudaFatCudaBinary *info = (__cudaFatCudaBinary *)fatCubin;
+ assert( info->version >= 3 );
+ unsigned num_ptx_versions=0;
+ unsigned max_capability=0;
+ unsigned selected_capability=0;
+ bool found=false;
+ unsigned forced_max_capability = context->get_device()->get_gpgpu()->get_config().get_forced_max_capability();
+ if (!info->ptx){
+ printf("ERROR: Cannot find ptx code in cubin file\n"
+ "\tIf you are using CUDA 4.0 or higher, please enable -gpgpu_ptx_use_cuobjdump or downgrade to CUDA 3.1\n");
+ exit(1);
+ }
+ while( info->ptx[num_ptx_versions].gpuProfileName != NULL ) {
+ unsigned capability=0;
+ sscanf(info->ptx[num_ptx_versions].gpuProfileName,"compute_%u",&capability);
+ printf("GPGPU-Sim PTX: __cudaRegisterFatBinary found PTX versions for '%s', ", info->ident);
+ printf("capability = %s\n", info->ptx[num_ptx_versions].gpuProfileName );
+ if( forced_max_capability ) {
+ if( capability > max_capability && capability <= forced_max_capability ) {
+ found = true;
+ max_capability=capability;
+ selected_capability = num_ptx_versions;
+ }
+ } else {
+ if( capability > max_capability ) {
+ found = true;
+ max_capability=capability;
+ selected_capability = num_ptx_versions;
+ }
+ }
+ num_ptx_versions++;
+ }
+ if( found ) {
+ printf("GPGPU-Sim PTX: Loading PTX for %s, capability = %s\n",
+ info->ident, info->ptx[selected_capability].gpuProfileName );
+ symbol_table *symtab;
+ const char *ptx = info->ptx[selected_capability].ptx;
+ if(context->get_device()->get_gpgpu()->get_config().convert_to_ptxplus() ) {
+ printf("GPGPU-Sim PTX: ERROR ** PTXPlus is only supported through cuobjdump\n"
+ "\tEither enable cuobjdump or disable PTXPlus in your configuration file\n");
+ exit(1);
+ } else {
+ symtab=ctx->gpgpu_ptx_sim_load_ptx_from_string(ptx,source_num);
+ context->add_binary(symtab,fat_cubin_handle);
+ ctx->gpgpu_ptxinfo_load_from_string( ptx, source_num, max_capability, context->no_of_ptx );
+ }
+ source_num++;
+ ctx->api->load_static_globals(symtab,STATIC_ALLOC_LIMIT,0xFFFFFFFF,context->get_device()->get_gpgpu());
+ ctx->api->load_constants(symtab,STATIC_ALLOC_LIMIT,context->get_device()->get_gpgpu());
+ } else {
+ printf("GPGPU-Sim PTX: warning -- did not find an appropriate PTX in cubin\n");
+ }
+ return (void**)fat_cubin_handle;
+ }
+#else
+ else {
+ printf("ERROR ** __cudaRegisterFatBinary() needs to be updated\n");
+ abort();
+ }
+#endif
+}
+
+void cudaRegisterFunctionInternal(
+ void **fatCubinHandle,
+ const char *hostFun,
+ char *deviceFun,
+ const char *deviceName,
+ int thread_limit,
+ uint3 *tid,
+ uint3 *bid,
+ dim3 *bDim,
+ dim3 *gDim,
+ gpgpu_context *gpgpu_ctx = NULL
+)
+{
+ gpgpu_context *ctx;
+ if (gpgpu_ctx){
+ ctx = gpgpu_ctx;
+ } else {
+ ctx = GPGPU_Context();
+ }
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ CUctx_st *context = GPGPUSim_Context();
+ unsigned fat_cubin_handle = (unsigned)(unsigned long long)fatCubinHandle;
+ printf("GPGPU-Sim PTX: __cudaRegisterFunction %s : hostFun 0x%p, fat_cubin_handle = %u\n",
+ deviceFun, hostFun, fat_cubin_handle);
+ if(context->get_device()->get_gpgpu()->get_config().use_cuobjdump())
+ ctx->cuobjdumpParseBinary(fat_cubin_handle);
+ context->register_function( fat_cubin_handle, hostFun, deviceFun );
+}
+
+void cudaRegisterVarInternal(
+ void **fatCubinHandle,
+ char *hostVar, //pointer to...something
+ char *deviceAddress, //name of variable
+ const char *deviceName, //name of variable (same as above)
+ int ext,
+ int size,
+ int constant,
+ int global,
+ gpgpu_context *gpgpu_ctx = NULL)
+{
+ gpgpu_context *ctx;
+ if (gpgpu_ctx){
+ ctx = gpgpu_ctx;
+ } else {
+ ctx = GPGPU_Context();
+ }
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ printf("GPGPU-Sim PTX: __cudaRegisterVar: hostVar = %p; deviceAddress = %s; deviceName = %s\n", hostVar, deviceAddress, deviceName);
+ printf("GPGPU-Sim PTX: __cudaRegisterVar: Registering const memory space of %d bytes\n", size);
+ if(GPGPUSim_Context()->get_device()->get_gpgpu()->get_config().use_cuobjdump())
+ ctx->cuobjdumpParseBinary((unsigned)(unsigned long long)fatCubinHandle);
+ fflush(stdout);
+ if ( constant && !global && !ext ) {
+ ctx->func_sim->gpgpu_ptx_sim_register_const_variable(hostVar,deviceName,size);
+ } else if ( !constant && !global && !ext ) {
+ ctx->func_sim->gpgpu_ptx_sim_register_global_variable(hostVar,deviceName,size);
+ } else cuda_not_implemented(__my_func__,__LINE__);
+}
+
+cudaError_t cudaConfigureCallInternal(dim3 gridDim, dim3 blockDim, size_t sharedMem, cudaStream_t stream, gpgpu_context* gpgpu_ctx = NULL)
+{
+ gpgpu_context *ctx;
+ if (gpgpu_ctx){
+ ctx = gpgpu_ctx;
+ } else {
+ ctx = GPGPU_Context();
+ }
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ struct CUstream_st *s = (struct CUstream_st *)stream;
+ ctx->api->g_cuda_launch_stack.push_back( kernel_config(gridDim,blockDim,sharedMem,s) );
+ return g_last_cudaError = cudaSuccess;
+}
+
+__host__ cudaError_t CUDARTAPI cudaGetDeviceCountInternal(int *count, gpgpu_context* gpgpu_ctx = NULL)
+{
+ gpgpu_context *ctx;
+ if (gpgpu_ctx){
+ ctx = gpgpu_ctx;
+ } else {
+ ctx = GPGPU_Context();
+ }
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ _cuda_device_id *dev = ctx->GPGPUSim_Init();
+ *count = dev->num_devices();
+ return g_last_cudaError = cudaSuccess;
+}
+
+__host__ cudaError_t CUDARTAPI cudaGetDevicePropertiesInternal(struct cudaDeviceProp *prop, int device, gpgpu_context* gpgpu_ctx = NULL)
+{
+ gpgpu_context *ctx;
+ if (gpgpu_ctx){
+ ctx = gpgpu_ctx;
+ } else {
+ ctx = GPGPU_Context();
+ }
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ _cuda_device_id *dev = ctx->GPGPUSim_Init();
+ if (device <= dev->num_devices() ) {
+ *prop= *dev->get_prop();
+ return g_last_cudaError = cudaSuccess;
+ } else {
+ return g_last_cudaError = cudaErrorInvalidDevice;
+ }
+}
+
+
+__host__ cudaError_t CUDARTAPI cudaChooseDeviceInternal(int *device, const struct cudaDeviceProp *prop, gpgpu_context* gpgpu_ctx = NULL)
+{
+ gpgpu_context *ctx;
+ if (gpgpu_ctx){
+ ctx = gpgpu_ctx;
+ } else {
+ ctx = GPGPU_Context();
+ }
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ _cuda_device_id *dev = ctx->GPGPUSim_Init();
+ *device = dev->get_id();
+ return g_last_cudaError = cudaSuccess;
+}
+
+cudaError_t cudaSetupArgumentInternal(const void *arg, size_t size, size_t offset, gpgpu_context* gpgpu_ctx = NULL)
+{
+ gpgpu_context *ctx;
+ if (gpgpu_ctx){
+ ctx = gpgpu_ctx;
+ } else {
+ ctx = GPGPU_Context();
+ }
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ gpgpusim_ptx_assert( !ctx->api->g_cuda_launch_stack.empty(), "empty launch stack" );
+ kernel_config &config = ctx->api->g_cuda_launch_stack.back();
+ config.set_arg(arg,size,offset);
+ printf("GPGPU-Sim PTX: Setting up arguments for %zu bytes starting at 0x%llx..\n",size, (unsigned long long) arg);
+
+ return g_last_cudaError = cudaSuccess;
+}
+
+cudaError_t cudaLaunchInternal( const char *hostFun, gpgpu_context* gpgpu_ctx = NULL )
+{
+ gpgpu_context *ctx;
+ if (gpgpu_ctx){
+ ctx = gpgpu_ctx;
+ } else {
+ ctx = GPGPU_Context();
+ }
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ CUctx_st* context = GPGPUSim_Context();
+ char *mode = getenv("PTX_SIM_MODE_FUNC");
+ if( mode )
+ sscanf(mode,"%u", &(ctx->func_sim->g_ptx_sim_mode));
+ gpgpusim_ptx_assert( !ctx->api->g_cuda_launch_stack.empty(), "empty launch stack" );
+ kernel_config config = ctx->api->g_cuda_launch_stack.back();
+ {
+ dim3 gridDim = config.grid_dim();
+ dim3 blockDim = config.block_dim();
+ if (gridDim.x * gridDim.y * gridDim.z == 0 || blockDim.x * blockDim.y * blockDim.z == 0)
+ {
+ //can't launch
+ printf("can't launch a empty kernel\n");
+ ctx->api->g_cuda_launch_stack.pop_back();
+ return g_last_cudaError = cudaErrorInvalidConfiguration;
+ }
+ }
+ struct CUstream_st *stream = config.get_stream();
+
+ printf("\nGPGPU-Sim PTX: cudaLaunch for 0x%p (mode=%s) on stream %u\n", hostFun,
+ (ctx->func_sim->g_ptx_sim_mode)?"functional simulation":"performance simulation", stream?stream->get_uid():0 );
+ kernel_info_t *grid = ctx->api->gpgpu_cuda_ptx_sim_init_grid(hostFun,config.get_args(),config.grid_dim(),config.block_dim(),context);
+ //do dynamic PDOM analysis for performance simulation scenario
+ std::string kname = grid->name();
+ function_info *kernel_func_info = grid->entry();
+ if (kernel_func_info->is_pdom_set()) {
+ printf("GPGPU-Sim PTX: PDOM analysis already done for %s \n", kname.c_str() );
+ } else {
+ printf("GPGPU-Sim PTX: finding reconvergence points for \'%s\'...\n", kname.c_str() );
+ kernel_func_info->do_pdom();
+ kernel_func_info->set_pdom();
+ }
+ dim3 gridDim = config.grid_dim();
+ dim3 blockDim = config.block_dim();
+
+ gpgpu_t *gpu = context->get_device()->get_gpgpu();
+ checkpoint *g_checkpoint;
+ g_checkpoint = new checkpoint();
+ class memory_space *global_mem;
+ global_mem = gpu->get_global_memory();
+
+ if(gpu->resume_option ==1 && (grid->get_uid()==gpu->resume_kernel))
+ {
+
+ char f1name[2048];
+ snprintf(f1name,2048,"checkpoint_files/global_mem_%d.txt", grid->get_uid());
+
+ g_checkpoint->load_global_mem(global_mem, f1name);
+ for (int i=0;i<gpu->resume_CTA;i++)
+ grid->increment_cta_id();
+ }
+ if(gpu->resume_option==1 && (grid->get_uid()<gpu->resume_kernel))
+ {
+ char f1name[2048];
+ snprintf(f1name,2048,"checkpoint_files/global_mem_%d.txt", grid->get_uid());
+
+ g_checkpoint->load_global_mem(global_mem, f1name);
+ printf("Skipping kernel %d as resuming from kernel %d\n",grid->get_uid(),gpu->resume_kernel );
+ ctx->api->g_cuda_launch_stack.pop_back();
+ return g_last_cudaError = cudaSuccess;
+
+ }
+ if(gpu->checkpoint_option==1 && (grid->get_uid()>gpu->checkpoint_kernel))
+ {
+ printf("Skipping kernel %d as checkpoint from kernel %d\n",grid->get_uid(),gpu->checkpoint_kernel );
+ ctx->api->g_cuda_launch_stack.pop_back();
+ return g_last_cudaError = cudaSuccess;
+
+ }
+ printf("GPGPU-Sim PTX: pushing kernel \'%s\' to stream %u, gridDim= (%u,%u,%u) blockDim = (%u,%u,%u) \n",
+ kname.c_str(), stream?stream->get_uid():0, gridDim.x,gridDim.y,gridDim.z,blockDim.x,blockDim.y,blockDim.z );
+ stream_operation op(grid,ctx->func_sim->g_ptx_sim_mode,stream);
+ g_stream_manager()->push(op);
+ ctx->api->g_cuda_launch_stack.pop_back();
+ return g_last_cudaError = cudaSuccess;
+}
+
+cudaError_t cudaMallocInternal(void **devPtr, size_t size, gpgpu_context* gpgpu_ctx = NULL)
+{
+ gpgpu_context *ctx;
+ if (gpgpu_ctx){
+ ctx = gpgpu_ctx;
+ } else {
+ ctx = GPGPU_Context();
+ }
if(g_debug_execution >= 3){
announce_call(__my_func__);
}
@@ -510,7 +964,7 @@ __host__ cudaError_t CUDARTAPI cudaMalloc(void **devPtr, size_t size)
*devPtr = context->get_device()->get_gpgpu()->gpu_malloc(size);
if(g_debug_execution >= 3){
printf("GPGPU-Sim PTX: cudaMallocing %zu bytes starting at 0x%llx..\n",size, (unsigned long long) *devPtr);
- g_mallocPtr_Size[(unsigned long long)*devPtr] = size;
+ ctx->api->g_mallocPtr_Size[(unsigned long long)*devPtr] = size;
}
if ( *devPtr ) {
return g_last_cudaError = cudaSuccess;
@@ -519,20 +973,270 @@ __host__ cudaError_t CUDARTAPI cudaMalloc(void **devPtr, size_t size)
}
}
-__host__ cudaError_t CUDARTAPI cudaMallocHost(void **ptr, size_t size)
+cudaError_t cudaMallocHostInternal(void **ptr, size_t size, gpgpu_context* gpgpu_ctx = NULL)
{
+ gpgpu_context *ctx;
+ if (gpgpu_ctx){
+ ctx = gpgpu_ctx;
+ } else {
+ ctx = GPGPU_Context();
+ }
if(g_debug_execution >= 3){
announce_call(__my_func__);
}
- GPGPUSim_Context();
*ptr = malloc(size);
if ( *ptr ) {
//track pinned memory size allocated in the host so that same amount of memory is also allocated in GPU.
- pinned_memory_size[*ptr]=size;
+ ctx->api->pinned_memory_size[*ptr]=size;
+ return g_last_cudaError = cudaSuccess;
+ } else {
+ return g_last_cudaError = cudaErrorMemoryAllocation;
+ }
+}
+
+cudaError_t cudaHostGetDevicePointerInternal(void **pDevice, void *pHost, unsigned int flags, gpgpu_context* gpgpu_ctx = NULL)
+{
+ gpgpu_context *ctx;
+ if (gpgpu_ctx){
+ ctx = gpgpu_ctx;
+ } else {
+ ctx = GPGPU_Context();
+ }
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ //only cpu memory allocation happens in cudaHostAlloc. Linking with device pointer to pinned memory happens here.
+ //TODO: once kernel is executed, the contents in global pointer of GPU must be copied back to CPU host pointer!
+ flags=0;
+ CUctx_st* context = GPGPUSim_Context();
+ gpgpu_t *gpu = context->get_device()->get_gpgpu();
+ std::map<void *, size_t>::const_iterator i = ctx->api->pinned_memory_size.find(pHost);
+ assert(i != ctx->api->pinned_memory_size.end());
+ size_t size = i->second;
+ *pDevice = gpu->gpu_malloc(size);
+ if(g_debug_execution >= 3){
+ printf("GPGPU-Sim PTX: cudaMallocing %zu bytes starting at 0x%llx..\n",size, (unsigned long long) *pDevice);
+ ctx->api->g_mallocPtr_Size[(unsigned long long)*pDevice] = size;
+ }
+ if ( *pDevice ) {
+ ctx->api->pinned_memory[pHost]=pDevice;
+ //Copy contents in cpu to gpu
+ gpu->memcpy_to_gpu((size_t)*pDevice,pHost,size);
+ return g_last_cudaError = cudaSuccess;
+ } else {
+ return g_last_cudaError = cudaErrorMemoryAllocation;
+ }
+}
+
+cudaError_t cudaGLMapBufferObjectInternal(void** devPtr, GLuint bufferObj, gpgpu_context* gpgpu_ctx = NULL)
+{
+ gpgpu_context *ctx;
+ if (gpgpu_ctx){
+ ctx = gpgpu_ctx;
+ } else {
+ ctx = GPGPU_Context();
+ }
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+#ifdef OPENGL_SUPPORT
+ GLint buffer_size=0;
+ CUctx_st* context = GPGPUSim_Context();
+
+ glbmap_entry_t *p = ctx->api->g_glbmap;
+ while ( p && p->m_bufferObj != bufferObj )
+ p = p->m_next;
+ if ( p == NULL ) {
+ glBindBuffer(GL_ARRAY_BUFFER,bufferObj);
+ glGetBufferParameteriv(GL_ARRAY_BUFFER,GL_BUFFER_SIZE,&buffer_size);
+ assert( buffer_size != 0 );
+ *devPtr = context->get_device()->get_gpgpu()->gpu_malloc(buffer_size);
+
+ // create entry and insert to front of list
+ glbmap_entry_t *n = (glbmap_entry_t *) calloc(1,sizeof(glbmap_entry_t));
+ n->m_next = ctx->api->g_glbmap;
+ ctx->api->g_glbmap = n;
+
+ // initialize entry
+ n->m_bufferObj = bufferObj;
+ n->m_devPtr = *devPtr;
+ n->m_size = buffer_size;
+
+ p = n;
+ } else {
+ buffer_size = p->m_size;
+ *devPtr = p->m_devPtr;
+ }
+
+ if ( *devPtr ) {
+ char *data = (char *) calloc(p->m_size,1);
+ glGetBufferSubData(GL_ARRAY_BUFFER,0,buffer_size,data);
+ memcpy_to_gpu( (size_t) *devPtr, data, buffer_size );
+ free(data);
+ printf("GPGPU-Sim PTX: cudaGLMapBufferObject %zu bytes starting at 0x%llx..\n", (size_t)buffer_size,
+ (unsigned long long) *devPtr);
return g_last_cudaError = cudaSuccess;
} else {
return g_last_cudaError = cudaErrorMemoryAllocation;
}
+
+ return g_last_cudaError = cudaSuccess;
+#else
+ fflush(stdout);
+ fflush(stderr);
+ printf("GPGPU-Sim PTX: GPGPU-Sim support for OpenGL integration disabled -- exiting\n");
+ fflush(stdout);
+ exit(50);
+#endif
+}
+
+#if CUDART_VERSION >= 6050
+CUresult
+cuLinkAddFileInternal(CUlinkState state, CUjitInputType type, const char *path,
+ unsigned int numOptions, CUjit_option *options, void **optionValues, gpgpu_context* gpgpu_ctx = NULL)
+{
+ gpgpu_context *ctx;
+ if (gpgpu_ctx){
+ ctx = gpgpu_ctx;
+ } else {
+ ctx = GPGPU_Context();
+ }
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ static bool addedFile = false;
+ if (addedFile){
+ printf("GPGPU-Sim PTX: ERROR: cuLinkAddFile does not support multiple files\n");
+ abort();
+ }
+
+ //blocking
+ assert(type==CU_JIT_INPUT_PTX);
+ CUctx_st *context = GPGPUSim_Context();
+ char *file = getenv("PTX_JIT_PATH");
+ if(file==NULL){
+ printf("GPGPU-Sim PTX: ERROR: PTX_JIT_PATH has not been set\n");
+ abort();
+ }
+ strcat(file,"/");
+ strcat(file,path);
+ symbol_table *symtab = ctx->gpgpu_ptx_sim_load_ptx_from_filename( file );
+ std::string fname(path);
+ ctx->api->name_symtab[fname] = symtab;
+ context->add_binary(symtab, 1);
+ ctx->api->load_static_globals(symtab,STATIC_ALLOC_LIMIT,0xFFFFFFFF,context->get_device()->get_gpgpu());
+ ctx->api->load_constants(symtab,STATIC_ALLOC_LIMIT,context->get_device()->get_gpgpu());
+ addedFile = true;
+ return CUDA_SUCCESS;
+}
+#endif
+
+#if (CUDART_VERSION >= 2010)
+
+cudaError_t cudaHostAllocInternal(void **pHost, size_t bytes, unsigned int flags, gpgpu_context* gpgpu_ctx = NULL)
+{
+ gpgpu_context *ctx;
+ if (gpgpu_ctx){
+ ctx = gpgpu_ctx;
+ } else {
+ ctx = GPGPU_Context();
+ }
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ *pHost = malloc(bytes);
+ //need to track the size allocated so that cudaHostGetDevicePointer() can function properly.
+ //TODO: vary this function behavior based on flags value (following nvidia documentation)
+ ctx->api->pinned_memory_size[*pHost]=bytes;
+ if( *pHost )
+ return g_last_cudaError = cudaSuccess;
+ else
+ return g_last_cudaError = cudaErrorMemoryAllocation;
+}
+
+#endif
+
+size_t getMaxThreadsPerBlock(struct cudaFuncAttributes *attr, gpgpu_context *ctx) {
+ _cuda_device_id *dev = ctx->GPGPUSim_Init();
+ struct cudaDeviceProp prop;
+
+ prop = *dev->get_prop();
+
+ size_t max = prop.maxThreadsPerBlock;
+
+ if (attr->numRegs && (prop.regsPerBlock / attr->numRegs) < max)
+ max = prop.regsPerBlock / attr->numRegs;
+
+ if (attr->sharedSizeBytes && (prop.sharedMemPerBlock / attr->sharedSizeBytes) < max)
+ max = prop.sharedMemPerBlock / attr->sharedSizeBytes;
+
+ return max;
+}
+
+cudaError_t CUDARTAPI cudaFuncGetAttributesInternal(struct cudaFuncAttributes *attr, const char *hostFun, gpgpu_context* gpgpu_ctx = NULL )
+{
+ gpgpu_context *ctx;
+ if (gpgpu_ctx){
+ ctx = gpgpu_ctx;
+ } else {
+ ctx = GPGPU_Context();
+ }
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ CUctx_st *context = GPGPUSim_Context();
+ function_info *entry = context->get_kernel(hostFun);
+ if( entry ) {
+ const struct gpgpu_ptx_sim_info *kinfo = entry->get_kernel_info();
+ attr->sharedSizeBytes = kinfo->smem;
+ attr->constSizeBytes = kinfo->cmem;
+ attr->localSizeBytes = kinfo->lmem;
+ attr->numRegs = kinfo->regs;
+ if(kinfo->maxthreads > 0)
+ attr->maxThreadsPerBlock = kinfo->maxthreads;
+ else
+ attr->maxThreadsPerBlock = getMaxThreadsPerBlock(attr, ctx);
+#if CUDART_VERSION >= 3000
+ attr->ptxVersion = kinfo->ptx_version;
+ attr->binaryVersion = kinfo->sm_target;
+#endif
+ }
+ return g_last_cudaError = cudaSuccess;
+}
+
+
+/*******************************************************************************
+ * *
+ * *
+ * *
+ *******************************************************************************/
+
+extern "C" {
+
+/*******************************************************************************
+ * *
+ * *
+ * *
+ *******************************************************************************/
+cudaError_t cudaPeekAtLastError(void)
+{
+ return g_last_cudaError;
+}
+
+__host__ cudaError_t CUDARTAPI cudaMalloc(void **devPtr, size_t size)
+{
+ return cudaMallocInternal(devPtr, size);
+}
+
+__host__ cudaError_t CUDARTAPI cudaMallocHost(void **ptr, size_t size)
+{
+ return cudaMallocHostInternal(ptr, size);
}
__host__ cudaError_t CUDARTAPI cudaMallocPitch(void **devPtr, size_t *pitch, size_t width, size_t height)
{
@@ -617,21 +1321,21 @@ __host__ cudaError_t CUDARTAPI cudaMemcpy(void *dst, const void *src, size_t cou
if(g_debug_execution >= 3)
printf("GPGPU-Sim PTX: cudaMemcpy(): devPtr = %p\n", dst);
if( kind == cudaMemcpyHostToDevice )
- g_stream_manager->push( stream_operation(src,(size_t)dst,count,0) );
+ g_stream_manager()->push( stream_operation(src,(size_t)dst,count,0) );
else if( kind == cudaMemcpyDeviceToHost )
- g_stream_manager->push( stream_operation((size_t)src,dst,count,0) );
+ g_stream_manager()->push( stream_operation((size_t)src,dst,count,0) );
else if( kind == cudaMemcpyDeviceToDevice )
- g_stream_manager->push( stream_operation((size_t)src,(size_t)dst,count,0) );
+ g_stream_manager()->push( stream_operation((size_t)src,(size_t)dst,count,0) );
else if ( kind == cudaMemcpyDefault ) {
if ((size_t)src >= GLOBAL_HEAP_START) {
if ((size_t)dst >= GLOBAL_HEAP_START)
- g_stream_manager->push( stream_operation((size_t)src,(size_t)dst,count,0) ); // device to device
+ g_stream_manager()->push( stream_operation((size_t)src,(size_t)dst,count,0) ); // device to device
else
- g_stream_manager->push( stream_operation((size_t)src,dst,count,0) ); // device to host
+ g_stream_manager()->push( stream_operation((size_t)src,dst,count,0) ); // device to host
}
else {
if ((size_t)dst >= GLOBAL_HEAP_START)
- g_stream_manager->push( stream_operation(src,(size_t)dst,count,0) );
+ g_stream_manager()->push( stream_operation(src,(size_t)dst,count,0) );
else {
printf("GPGPU-Sim PTX: cudaMemcpy - ERROR : unsupported transfer: host to host\n");
abort();
@@ -773,7 +1477,7 @@ __host__ cudaError_t CUDARTAPI cudaMemcpyToSymbol(const char *symbol, const void
assert(kind == cudaMemcpyHostToDevice);
printf("GPGPU-Sim PTX: cudaMemcpyToSymbol: symbol = %p\n", symbol);
//stream_operation( const char *symbol, const void *src, size_t count, size_t offset )
- g_stream_manager->push( stream_operation(src,symbol,count,offset,0) );
+ g_stream_manager()->push( stream_operation(src,symbol,count,offset,0) );
//gpgpu_ptx_sim_memcpy_symbol(symbol,src,count,offset,1,context->get_device()->get_gpgpu());
return g_last_cudaError = cudaSuccess;
}
@@ -787,7 +1491,7 @@ __host__ cudaError_t CUDARTAPI cudaMemcpyFromSymbol(void *dst, const char *symbo
//CUctx_st *context = GPGPUSim_Context();
assert(kind == cudaMemcpyDeviceToHost);
printf("GPGPU-Sim PTX: cudaMemcpyFromSymbol: symbol = %p\n", symbol);
- g_stream_manager->push( stream_operation(symbol,dst,count,offset,0) );
+ g_stream_manager()->push( stream_operation(symbol,dst,count,offset,0) );
//gpgpu_ptx_sim_memcpy_symbol(symbol,dst,count,offset,0,context->get_device()->get_gpgpu());
return g_last_cudaError = cudaSuccess;
}
@@ -816,9 +1520,9 @@ __host__ cudaError_t CUDARTAPI cudaMemcpyAsync(void *dst, const void *src, size_
}
struct CUstream_st *s = (struct CUstream_st *)stream;
switch( kind ) {
- case cudaMemcpyHostToDevice: g_stream_manager->push( stream_operation(src,(size_t)dst,count,s) ); break;
- case cudaMemcpyDeviceToHost: g_stream_manager->push( stream_operation((size_t)src,dst,count,s) ); break;
- case cudaMemcpyDeviceToDevice: g_stream_manager->push( stream_operation((size_t)src,(size_t)dst,count,s) ); break;
+ case cudaMemcpyHostToDevice: g_stream_manager()->push( stream_operation(src,(size_t)dst,count,s) ); break;
+ case cudaMemcpyDeviceToHost: g_stream_manager()->push( stream_operation((size_t)src,dst,count,s) ); break;
+ case cudaMemcpyDeviceToDevice: g_stream_manager()->push( stream_operation((size_t)src,(size_t)dst,count,s) ); break;
default:
abort();
}
@@ -875,105 +1579,6 @@ __host__ cudaError_t CUDARTAPI cudaMemcpy2DFromArrayAsync(void *dst, size_t dpit
return g_last_cudaError = cudaErrorUnknown;
}
-
-
-/*******************************************************************************
- * *
- * *
- * *
- *******************************************************************************/
-
-__host__ cudaError_t CUDARTAPI cudaMemset(void *mem, int c, size_t count)
-{
- if(g_debug_execution >= 3){
- announce_call(__my_func__);
- }
- CUctx_st *context = GPGPUSim_Context();
- gpgpu_t *gpu = context->get_device()->get_gpgpu();
- gpu->gpu_memset((size_t)mem, c, count);
- return g_last_cudaError = cudaSuccess;
-}
-
-//memset operation is done but i think its not async?
-__host__ cudaError_t CUDARTAPI cudaMemsetAsync(void *mem, int c, size_t count, cudaStream_t stream=0)
-{
- if(g_debug_execution >= 3){
- announce_call(__my_func__);
- }
- printf("GPGPU-Sim PTX: WARNING: Asynchronous memset not supported (%s)\n", __my_func__);
- CUctx_st *context = GPGPUSim_Context();
- gpgpu_t *gpu = context->get_device()->get_gpgpu();
- gpu->gpu_memset((size_t)mem, c, count);
- return g_last_cudaError = cudaSuccess;
-}
-
-__host__ cudaError_t CUDARTAPI cudaMemset2D(void *mem, size_t pitch, int c, size_t width, size_t height)
-{
- if(g_debug_execution >= 3){
- announce_call(__my_func__);
- }
- cuda_not_implemented(__my_func__,__LINE__);
- return g_last_cudaError = cudaErrorUnknown;
-}
-
-
-
-/*******************************************************************************
- * *
- * *
- * *
- *******************************************************************************/
-
-__host__ cudaError_t CUDARTAPI cudaGetSymbolAddress(void **devPtr, const char *symbol)
-{
- if(g_debug_execution >= 3){
- announce_call(__my_func__);
- }
- cuda_not_implemented(__my_func__,__LINE__);
- return g_last_cudaError = cudaErrorUnknown;
-}
-
-
-__host__ cudaError_t CUDARTAPI cudaGetSymbolSize(size_t *size, const char *symbol)
-{
- if(g_debug_execution >= 3){
- announce_call(__my_func__);
- }
- cuda_not_implemented(__my_func__,__LINE__);
- return g_last_cudaError = cudaErrorUnknown;
-}
-
-
-
-/*******************************************************************************
- * *
- * *
- * *
- *******************************************************************************/
-__host__ cudaError_t CUDARTAPI cudaGetDeviceCount(int *count)
-{
- if(g_debug_execution >= 3){
- announce_call(__my_func__);
- }
- _cuda_device_id *dev = GPGPUSim_Init();
- *count = dev->num_devices();
- return g_last_cudaError = cudaSuccess;
-}
-
-__host__ cudaError_t CUDARTAPI cudaGetDeviceProperties(struct cudaDeviceProp *prop, int device)
-{
- if(g_debug_execution >= 3){
- announce_call(__my_func__);
- }
- _cuda_device_id *dev = GPGPUSim_Init();
- if (device <= dev->num_devices() ) {
- *prop= *dev->get_prop();
- return g_last_cudaError = cudaSuccess;
- } else {
- return g_last_cudaError = cudaErrorInvalidDevice;
- }
-}
-
#if (CUDART_VERSION >= 8000)
cudaError_t CUDARTAPI cudaOccupancyMaxActiveBlocksPerMultiprocessorWithFlags(int* numBlocks, const char *hostFunc, int blockSize, size_t dynamicSMemSize, unsigned int flags)
{
@@ -1003,13 +1608,38 @@ cudaError_t CUDARTAPI cudaOccupancyMaxActiveBlocksPerMultiprocessorWithFlags(int
#endif
#if (CUDART_VERSION > 5000)
-__host__ cudaError_t CUDARTAPI cudaDeviceGetAttribute(int *value, enum cudaDeviceAttr attr, int device)
+
+/*******************************************************************************
+ * *
+ * *
+ * *
+ *******************************************************************************/
+__host__ cudaError_t CUDARTAPI cudaMemset(void *mem, int c, size_t count)
{
if(g_debug_execution >= 3){
announce_call(__my_func__);
}
+ CUctx_st *context = GPGPUSim_Context();
+ gpgpu_t *gpu = context->get_device()->get_gpgpu();
+ gpu->gpu_memset((size_t)mem, c, count);
+ return g_last_cudaError = cudaSuccess;
+}
+
+__host__ cudaError_t CUDARTAPI cudaDeviceGetAttributeInternal(int *value, enum cudaDeviceAttr attr, int device, gpgpu_context* gpgpu_ctx = NULL)
+{
+ gpgpu_context *ctx;
+ if (gpgpu_ctx){
+ ctx = gpgpu_ctx;
+ } else {
+ ctx = GPGPU_Context();
+ }
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+
const struct cudaDeviceProp *prop;
- _cuda_device_id *dev = GPGPUSim_Init();
+ _cuda_device_id *dev = ctx->GPGPUSim_Init();
+
if (device <= dev->num_devices() ) {
prop = dev->get_prop();
switch (attr) {
@@ -1193,82 +1823,98 @@ __host__ cudaError_t CUDARTAPI cudaDeviceGetAttribute(int *value, enum cudaDevic
return g_last_cudaError = cudaErrorInvalidDevice;
}
}
-#endif
-__host__ cudaError_t CUDARTAPI cudaChooseDevice(int *device, const struct cudaDeviceProp *prop)
+//memset operation is done but i think its not async?
+__host__ cudaError_t CUDARTAPI cudaMemsetAsync(void *mem, int c, size_t count, cudaStream_t stream=0)
{
if(g_debug_execution >= 3){
announce_call(__my_func__);
}
- _cuda_device_id *dev = GPGPUSim_Init();
- *device = dev->get_id();
+ printf("GPGPU-Sim PTX: WARNING: Asynchronous memset not supported (%s)\n", __my_func__);
+ CUctx_st *context = GPGPUSim_Context();
+ gpgpu_t *gpu = context->get_device()->get_gpgpu();
+ gpu->gpu_memset((size_t)mem, c, count);
return g_last_cudaError = cudaSuccess;
}
-__host__ cudaError_t CUDARTAPI cudaSetDevice(int device)
+__host__ cudaError_t CUDARTAPI cudaMemset2D(void *mem, size_t pitch, int c, size_t width, size_t height)
{
if(g_debug_execution >= 3){
announce_call(__my_func__);
}
- //set the active device to run cuda
- if ( device <= GPGPUSim_Init()->num_devices() ) {
- g_active_device = device;
- return g_last_cudaError = cudaSuccess;
- } else {
- return g_last_cudaError = cudaErrorInvalidDevice;
- }
+ cuda_not_implemented(__my_func__,__LINE__);
+ return g_last_cudaError = cudaErrorUnknown;
}
-__host__ cudaError_t CUDARTAPI cudaGetDevice(int *device)
+
+
+/*******************************************************************************
+ * *
+ * *
+ * *
+ *******************************************************************************/
+
+__host__ cudaError_t CUDARTAPI cudaGetSymbolAddress(void **devPtr, const char *symbol)
{
if(g_debug_execution >= 3){
announce_call(__my_func__);
}
- *device = g_active_device;
- return g_last_cudaError = cudaSuccess;
+ cuda_not_implemented(__my_func__,__LINE__);
+ return g_last_cudaError = cudaErrorUnknown;
}
-__host__ cudaError_t CUDARTAPI cudaDeviceGetLimit ( size_t* pValue, cudaLimit limit )
+
+__host__ cudaError_t CUDARTAPI cudaGetSymbolSize(size_t *size, const char *symbol)
{
if(g_debug_execution >= 3){
- announce_call(__my_func__);
- }
- _cuda_device_id *dev = GPGPUSim_Init();
- const struct cudaDeviceProp *prop = dev->get_prop();
- const gpgpu_sim_config& config=dev->get_gpgpu()->get_config();
- switch(limit) {
- case 0: // cudaLimitStackSize
- *pValue=config.stack_limit();
- break;
- case 2: // cudaLimitMallocHeapSize
- *pValue=config.heap_limit();
- break;
-#if (CUDART_VERSION > 5050)
- case 3: // cudaLimitDevRuntimeSyncDepth
- if(prop->major > 2){
- *pValue=config.sync_depth_limit();
- break;
- }
- else{
- printf("ERROR:Limit %s is not supported on this architecture \n",limit);
- abort();
- }
- case 4: // cudaLimitDevRuntimePendingLaunchCount
- if(prop->major > 2){
- *pValue=config.pending_launch_count_limit();
- break;
- }
- else{
- printf("ERROR:Limit %s is not supported on this architecture \n",limit);
- abort();
- }
+ announce_call(__my_func__);
+ }
+ cuda_not_implemented(__my_func__,__LINE__);
+ return g_last_cudaError = cudaErrorUnknown;
+}
+
+
+
+/*******************************************************************************
+ * *
+ * *
+ * *
+ *******************************************************************************/
+__host__ cudaError_t CUDARTAPI cudaGetDeviceCount(int *count)
+{
+ return cudaGetDeviceCountInternal(count);
+}
+
+__host__ cudaError_t CUDARTAPI cudaGetDeviceProperties(struct cudaDeviceProp *prop, int device)
+{
+ return cudaGetDevicePropertiesInternal(prop, device);
+}
+
+#if (CUDART_VERSION > 5000)
+__host__ cudaError_t CUDARTAPI cudaDeviceGetAttribute(int *value, enum cudaDeviceAttr attr, int device)
+{
+ return cudaDeviceGetAttributeInternal(value, attr, device);
+}
#endif
- default:
- printf("ERROR:Limit %s unimplemented \n",limit);
- abort();
- }
- return g_last_cudaError = cudaSuccess;
+__host__ cudaError_t CUDARTAPI cudaChooseDevice(int *device, const struct cudaDeviceProp *prop)
+{
+ return cudaChooseDeviceInternal(device, prop);
+}
+
+__host__ cudaError_t CUDARTAPI cudaSetDevice(int device)
+{
+ return cudaSetDeviceInternal(device);
+}
+
+__host__ cudaError_t CUDARTAPI cudaGetDevice(int *device)
+{
+ return cudaGetDeviceInternal(device);
+}
+
+__host__ cudaError_t CUDARTAPI cudaDeviceGetLimit( size_t* pValue, cudaLimit limit )
+{
+ return cudaDeviceGetLimitInternal( pValue, limit );
}
__host__ cudaError_t CUDARTAPI cudaStreamGetPriority ( cudaStream_t hStream, int* priority )
@@ -1466,131 +2112,35 @@ __host__ const char* CUDARTAPI cudaGetErrorString(cudaError_t error)
return strdup(buf);
}
-__host__ cudaError_t CUDARTAPI cudaConfigureCall(dim3 gridDim, dim3 blockDim, size_t sharedMem, cudaStream_t stream)
-{
- if(g_debug_execution >= 3){
- announce_call(__my_func__);
- }
- struct CUstream_st *s = (struct CUstream_st *)stream;
- g_cuda_launch_stack.push_back( kernel_config(gridDim,blockDim,sharedMem,s) );
- return g_last_cudaError = cudaSuccess;
-}
-
__host__ cudaError_t CUDARTAPI cudaSetupArgument(const void *arg, size_t size, size_t offset)
{
- if(g_debug_execution >= 3){
- announce_call(__my_func__);
- }
- gpgpusim_ptx_assert( !g_cuda_launch_stack.empty(), "empty launch stack" );
- kernel_config &config = g_cuda_launch_stack.back();
- config.set_arg(arg,size,offset);
- printf("GPGPU-Sim PTX: Setting up arguments for %zu bytes starting at 0x%llx..\n",size, (unsigned long long) arg);
-
- return g_last_cudaError = cudaSuccess;
+ return cudaSetupArgumentInternal(arg, size, offset);
}
__host__ cudaError_t CUDARTAPI cudaLaunch( const char *hostFun )
{
- if(g_debug_execution >= 3){
- announce_call(__my_func__);
- }
- CUctx_st* context = GPGPUSim_Context();
- char *mode = getenv("PTX_SIM_MODE_FUNC");
- if( mode )
- sscanf(mode,"%u", &g_ptx_sim_mode);
- gpgpusim_ptx_assert( !g_cuda_launch_stack.empty(), "empty launch stack" );
- kernel_config config = g_cuda_launch_stack.back();
- {
- dim3 gridDim = config.grid_dim();
- dim3 blockDim = config.block_dim();
- //if (gridDim.x * gridDim.y * gridDim.z == 0 || blockDim.x * blockDim.y * blockDim.z == 0)
- //{
- //can't launch
- // printf("can't launch a empty kernel\n");
- // g_cuda_launch_stack.pop_back();
- // return g_last_cudaError = cudaErrorInvalidConfiguration;
- //}
- }
- struct CUstream_st *stream = config.get_stream();
- if(g_stream_manager->is_blocking())
- stream = 0;
-
- printf("\nGPGPU-Sim PTX: cudaLaunch for 0x%p (mode=%s) on stream %u\n", hostFun,
- g_ptx_sim_mode?"functional simulation":"performance simulation", stream?stream->get_uid():0 );
- kernel_info_t *grid = gpgpu_cuda_ptx_sim_init_grid(hostFun,config.get_args(),config.grid_dim(),config.block_dim(),context);
- //do dynamic PDOM analysis for performance simulation scenario
- std::string kname = grid->name();
- function_info *kernel_func_info = grid->entry();
- if (kernel_func_info->is_pdom_set()) {
- printf("GPGPU-Sim PTX: PDOM analysis already done for %s \n", kname.c_str() );
- } else {
- printf("GPGPU-Sim PTX: finding reconvergence points for \'%s\'...\n", kname.c_str() );
- kernel_func_info->do_pdom();
- kernel_func_info->set_pdom();
- }
- dim3 gridDim = config.grid_dim();
- dim3 blockDim = config.block_dim();
-
- gpgpu_t *gpu = context->get_device()->get_gpgpu();
- checkpoint *g_checkpoint;
- g_checkpoint = new checkpoint();
- class memory_space *global_mem;
- global_mem = gpu->get_global_memory();
-
- if(gpu->resume_option ==1 && (grid->get_uid()==gpu->resume_kernel))
- {
-
- char f1name[2048];
- snprintf(f1name,2048,"checkpoint_files/global_mem_%d.txt", grid->get_uid());
-
- g_checkpoint->load_global_mem(global_mem, f1name);
- for (int i=0;i<gpu->resume_CTA;i++)
- grid->increment_cta_id();
- }
- if(gpu->resume_option==1 && (grid->get_uid()<gpu->resume_kernel))
- {
- char f1name[2048];
- snprintf(f1name,2048,"checkpoint_files/global_mem_%d.txt", grid->get_uid());
-
- g_checkpoint->load_global_mem(global_mem, f1name);
- printf("Skipping kernel %d as resuming from kernel %d\n",grid->get_uid(),gpu->resume_kernel );
- g_cuda_launch_stack.pop_back();
- return g_last_cudaError = cudaSuccess;
-
- }
- if(gpu->checkpoint_option==1 && (grid->get_uid()>gpu->checkpoint_kernel))
- {
- printf("Skipping kernel %d as checkpoint from kernel %d\n",grid->get_uid(),gpu->checkpoint_kernel );
- g_cuda_launch_stack.pop_back();
- return g_last_cudaError = cudaSuccess;
-
- }
- printf("GPGPU-Sim PTX: pushing kernel \'%s\' to stream %u, gridDim= (%u,%u,%u) blockDim = (%u,%u,%u) \n",
- kname.c_str(), stream?stream->get_uid():0, gridDim.x,gridDim.y,gridDim.z,blockDim.x,blockDim.y,blockDim.z );
- stream_operation op(grid,g_ptx_sim_mode,stream);
- g_stream_manager->push(op);
- g_cuda_launch_stack.pop_back();
- return g_last_cudaError = cudaSuccess;
+ return cudaLaunchInternal( hostFun );
}
__host__ cudaError_t CUDARTAPI cudaLaunchKernel ( const char* hostFun, dim3 gridDim, dim3 blockDim, const void** args, size_t sharedMem, cudaStream_t stream )
{
- if(g_debug_execution >= 3){
- announce_call(__my_func__);
- }
- CUctx_st *context = GPGPUSim_Context();
- function_info *entry = context->get_kernel(hostFun);
-
- cudaConfigureCall(gridDim, blockDim, sharedMem, stream);
- for(unsigned i = 0; i < entry->num_args(); i++){
- std::pair<size_t, unsigned> p = entry->get_param_config(i);
- cudaSetupArgument(args[i], p.first, p.second);
- }
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ CUctx_st *context = GPGPUSim_Context();
+ function_info *entry = context->get_kernel(hostFun);
+#if CUDART_VERSION < 10000
+ cudaConfigureCallInternal(gridDim, blockDim, sharedMem, stream);
+#endif
+ for(unsigned i = 0; i < entry->num_args(); i++){
+ std::pair<size_t, unsigned> p = entry->get_param_config(i);
+ cudaSetupArgumentInternal(args[i], p.first, p.second);
+ }
- cudaLaunch(hostFun);
- return g_last_cudaError = cudaSuccess;
+ cudaLaunchInternal(hostFun);
+ return g_last_cudaError = cudaSuccess;
}
@@ -1608,7 +2158,7 @@ __host__ cudaError_t CUDARTAPI cudaStreamCreate(cudaStream_t *stream)
printf("GPGPU-Sim PTX: cudaStreamCreate\n");
#if (CUDART_VERSION >= 3000)
*stream = new struct CUstream_st();
- g_stream_manager->add_stream(*stream);
+ g_stream_manager()->add_stream(*stream);
#else
*stream = 0;
printf("GPGPU-Sim PTX: WARNING: Asynchronous kernel execution not supported (%s)\n", __my_func__);
@@ -1647,7 +2197,7 @@ __host__ cudaError_t CUDARTAPI cudaStreamDestroy(cudaStream_t stream)
//per-stream synchronization required for application using external libraries without explicit synchronization in the code to
//avoid the stream_manager from spinning forever to destroy non-empty streams without making any forward progress.
stream->synchronize();
- g_stream_manager->destroy_stream(stream);
+ g_stream_manager()->destroy_stream(stream);
#endif
return g_last_cudaError = cudaSuccess;
}
@@ -1727,7 +2277,7 @@ __host__ cudaError_t CUDARTAPI cudaEventRecord(cudaEvent_t event, cudaStream_t s
if( !e ) return g_last_cudaError = cudaErrorUnknown;
struct CUstream_st *s = (struct CUstream_st *)stream;
stream_operation op(e,s);
- g_stream_manager->push(op);
+ g_stream_manager()->push(op);
return g_last_cudaError = cudaSuccess;
}
@@ -1743,11 +2293,11 @@ __host__ cudaError_t CUDARTAPI cudaStreamWaitEvent(cudaStream_t stream, cudaEven
return g_last_cudaError = cudaSuccess;
}
if (!stream){
- g_stream_manager->pushCudaStreamWaitEventToAllStreams(e, flags);
+ g_stream_manager()->pushCudaStreamWaitEventToAllStreams(e, flags);
} else {
struct CUstream_st *s = (struct CUstream_st *)stream;
stream_operation op(s,e,flags);
- g_stream_manager->push(op);
+ g_stream_manager()->push(op);
}
return g_last_cudaError = cudaSuccess;
}
@@ -1898,178 +2448,8 @@ __host__ cudaError_t CUDARTAPI cudaGetExportTable(const void **ppExportTable, co
//#include "../../cuobjdump_to_ptxplus/cuobjdump_parser.h"
-enum cuobjdumpSectionType {
- PTXSECTION=0,
- ELFSECTION
-};
-
-
-class cuobjdumpSection {
-public:
- //Constructor
- cuobjdumpSection() {
- arch = 0;
- identifier = "";
- }
- virtual ~cuobjdumpSection() {}
- unsigned getArch() {return arch;}
- void setArch(unsigned a) {arch = a;}
- std::string getIdentifier() {return identifier;}
- void setIdentifier(std::string i) {identifier = i;}
- virtual void print(){std::cout << "cuobjdump Section: unknown type" << std::endl;}
-private:
- unsigned arch;
- std::string identifier;
-};
-
-class cuobjdumpELFSection : public cuobjdumpSection
-{
-public:
- cuobjdumpELFSection() {}
- virtual ~cuobjdumpELFSection() {
- elffilename = "";
- sassfilename = "";
- }
- std::string getELFfilename() {return elffilename;}
- void setELFfilename(std::string f) {elffilename = f;}
- std::string getSASSfilename() {return sassfilename;}
- void setSASSfilename(std::string f) {sassfilename = f;}
- virtual void print() {
- std::cout << "ELF Section:" << std::endl;
- std::cout << "arch: sm_" << getArch() << std::endl;
- std::cout << "identifier: " << getIdentifier() << std::endl;
- std::cout << "elf filename: " << getELFfilename() << std::endl;
- std::cout << "sass filename: " << getSASSfilename() << std::endl;
- std::cout << std::endl;
- }
-private:
- std::string elffilename;
- std::string sassfilename;
-};
-
-class cuobjdumpPTXSection : public cuobjdumpSection
-{
-public:
- cuobjdumpPTXSection(){
- ptxfilename = "";
- }
- std::string getPTXfilename() {return ptxfilename;}
- void setPTXfilename(std::string f) {ptxfilename = f;}
- virtual void print() {
- std::cout << "PTX Section:" << std::endl;
- std::cout << "arch: sm_" << getArch() << std::endl;
- std::cout << "identifier: " << getIdentifier() << std::endl;
- std::cout << "ptx filename: " << getPTXfilename() << std::endl;
- std::cout << std::endl;
- }
-private:
- std::string ptxfilename;
-};
-
-std::list<cuobjdumpSection*> cuobjdumpSectionList;
-std::list<cuobjdumpSection*> libSectionList;
-
-// sectiontype: 0 for ptx, 1 for elf
-void addCuobjdumpSection(int sectiontype){
- if (sectiontype)
- cuobjdumpSectionList.push_front(new cuobjdumpELFSection());
- else
- cuobjdumpSectionList.push_front(new cuobjdumpPTXSection());
- printf("## Adding new section %s\n", sectiontype?"ELF":"PTX");
-}
-
-void setCuobjdumparch(const char* arch){
- unsigned archnum;
- sscanf(arch, "sm_%u", &archnum);
- assert (archnum && "cannot have sm_0");
- printf("Adding arch: %s\n", arch);
- cuobjdumpSectionList.front()->setArch(archnum);
-}
-
-void setCuobjdumpidentifier(const char* identifier){
- printf("Adding identifier: %s\n", identifier);
- cuobjdumpSectionList.front()->setIdentifier(identifier);
-}
-
-void setCuobjdumpptxfilename(const char* filename){
- printf("Adding ptx filename: %s\n", filename);
- cuobjdumpSection* x = cuobjdumpSectionList.front();
- if (dynamic_cast<cuobjdumpPTXSection*>(x) == NULL){
- assert (0 && "You shouldn't be trying to add a ptxfilename to an elf section");
- }
- (dynamic_cast<cuobjdumpPTXSection*>(x))->setPTXfilename(filename);
-}
-
-void setCuobjdumpelffilename(const char* filename){
- if (dynamic_cast<cuobjdumpELFSection*>(cuobjdumpSectionList.front()) == NULL){
- assert (0 && "You shouldn't be trying to add a elffilename to an ptx section");
- }
- (dynamic_cast<cuobjdumpELFSection*>(cuobjdumpSectionList.front()))->setELFfilename(filename);
-}
-
-void setCuobjdumpsassfilename(const char* filename){
- if (dynamic_cast<cuobjdumpELFSection*>(cuobjdumpSectionList.front()) == NULL){
- assert (0 && "You shouldn't be trying to add a sassfilename to an ptx section");
- }
- (dynamic_cast<cuobjdumpELFSection*>(cuobjdumpSectionList.front()))->setSASSfilename(filename);
-}
-extern int cuobjdump_parse();
-extern FILE *cuobjdump_in;
-
-//! Return the executable file of the process containing the PTX/SASS code
-//!
-//! This Function returns the executable file ran by the process. This
-//! executable is supposed to contain the PTX/SASS code. It provides workaround
-//! for processes running on valgrind by dereferencing /proc/<pid>/exe within the
-//! GPGPU-Sim process before calling cuobjdump to extract PTX/SASS. This is
-//! needed because valgrind uses x86 emulation to detect memory leak. Other
-//! processes (e.g. cuobjdump) reading /proc/<pid>/exe will see the emulator
-//! executable instead of the application binary.
-//!
-std::string get_app_binary(){
- char self_exe_path[1025];
-#ifdef __APPLE__
- uint32_t size = sizeof(self_exe_path);
- if( _NSGetExecutablePath(self_exe_path,&size) != 0 ) {
- printf("GPGPU-Sim ** ERROR: _NSGetExecutablePath input buffer too small\n");
- exit(1);
- }
-#else
- std::stringstream exec_link;
- exec_link << "/proc/self/exe";
-
- ssize_t path_length = readlink(exec_link.str().c_str(), self_exe_path, 1024);
- assert(path_length != -1);
- self_exe_path[path_length] = '\0';
-#endif
-
- printf("self exe links to: %s\n", self_exe_path);
- return self_exe_path;
-}
-
-//above func gives abs path whereas this give just the name of application.
-char* get_app_binary_name(std::string abs_path){
- char *self_exe_path;
-#ifdef __APPLE__
- //TODO: get apple device and check the result.
- printf("WARNING: not tested for Apple-mac devices \n");
- abort();
-#else
- char* buf = strdup(abs_path.c_str());
- char *token = strtok(buf, "/");
- while(token !=NULL){
- self_exe_path = token;
- token = strtok(NULL,"/");
- }
-#endif
- self_exe_path = strtok(self_exe_path, ".");
- printf("self exe links to: %s\n", self_exe_path);
- return self_exe_path;
-}
-
//extracts all ptx files from binary and dumps into prog_name.unique_no.sm_<>.ptx files
-void extract_ptx_files_using_cuobjdump(){
- extern bool g_cdp_enabled;
+void cuda_runtime_api::extract_ptx_files_using_cuobjdump(CUctx_st *context){
char command[1000];
char *pytorch_bin = getenv("PYTORCH_BIN");
std::string app_binary = get_app_binary();
@@ -2090,7 +2470,7 @@ void extract_ptx_files_using_cuobjdump(){
printf("WARNING: Failed to execute cuobjdump to get list of ptx files \n");
exit(0);
}
- if(!g_cdp_enabled) {
+ if(!gpgpu_ctx->device_runtime->g_cdp_enabled) {
//based on the list above, dump ptx files individually. Format of dumped ptx file is prog_name.unique_no.sm_<>.ptx
std::ifstream infile(ptx_list_file_name);
@@ -2105,11 +2485,11 @@ void extract_ptx_files_using_cuobjdump(){
printf("ERROR: command: %s failed \n",command);
exit(0);
}
- no_of_ptx++;
+ context->no_of_ptx++;
}
}
- if(!no_of_ptx){
+ if(!context->no_of_ptx){
printf("WARNING: Number of ptx in the executable file are 0. One of the reasons might be\n");
printf("\t1. CDP is enabled\n");
printf("\t2. When using PyTorch, PYTORCH_BIN is not set correctly\n");
@@ -2137,28 +2517,6 @@ void extract_ptx_files_using_cuobjdump(){
}
-static int get_app_cuda_version() {
- int app_cuda_version = 0;
- char fname[1024];
- snprintf(fname,1024,"_app_cuda_version_XXXXXX");
- int fd=mkstemp(fname);
- close(fd);
- std::string app_cuda_version_command = "ldd " + get_app_binary() + " | grep libcudart.so | sed 's/.*libcudart.so.\\(.*\\) =>.*/\\1/' > " + fname;
- system(app_cuda_version_command.c_str());
- FILE * cmd = fopen(fname, "r");
- char buf[256];
- while (fgets(buf, sizeof(buf), cmd) != 0) {
- std::cout << buf;
- app_cuda_version = atoi(buf);
- }
- fclose(cmd);
- if ( app_cuda_version == 0 ) {
- printf( "Error - Cannot detect the app's CUDA version.\n" );
- exit(1);
- }
- return app_cuda_version;
-}
-
//! Call cuobjdump to extract everything (-elf -sass -ptx)
/*!
@@ -2168,7 +2526,7 @@ static int get_app_cuda_version() {
* It is also responsible for extracting the libraries linked to the binary if the option is
* enabled
* */
-void extract_code_using_cuobjdump(){
+void cuda_runtime_api::extract_code_using_cuobjdump(){
CUctx_st *context = GPGPUSim_Context();
unsigned forced_max_capability = context->get_device()->get_gpgpu()->get_config().get_forced_max_capability();
@@ -2185,12 +2543,11 @@ void extract_code_using_cuobjdump(){
}
// Running cuobjdump using dynamic link to current process
// Needs the option '-all' to extract PTX from CDP-enabled binary
- extern bool g_cdp_enabled;
//dump ptx for all individial ptx files into sepearte files which is later used by ptxas.
int result=0;
#if (CUDART_VERSION >= 6000)
- extract_ptx_files_using_cuobjdump();
+ extract_ptx_files_using_cuobjdump(context);
return;
#endif
//TODO: redundant to dump twice. how can it be prevented?
@@ -2200,7 +2557,7 @@ void extract_code_using_cuobjdump(){
snprintf(fname,1024,"_cuobjdump_complete_output_XXXXXX");
int fd=mkstemp(fname);
close(fd);
- if(!g_cdp_enabled)
+ if(!gpgpu_ctx->device_runtime->g_cdp_enabled)
snprintf(command,1000,"$CUDA_INSTALL_PATH/bin/cuobjdump -ptx -elf -sass %s > %s", app_binary.c_str(), fname);
else
snprintf(command,1000,"$CUDA_INSTALL_PATH/bin/cuobjdump -ptx -elf -sass -all %s > %s", app_binary.c_str(), fname);
@@ -2223,9 +2580,16 @@ void extract_code_using_cuobjdump(){
if (parse_output) {
printf("Parsing file %s\n", fname);
+ FILE *cuobjdump_in;
cuobjdump_in = fopen(fname, "r");
- cuobjdump_parse();
+ struct cuobjdump_parser parser;
+ parser.elfserial = 1;
+ parser.ptxserial = 1;
+ cuobjdump_lex_init(&(parser.scanner));
+ cuobjdump_set_in(cuobjdump_in, (parser.scanner));
+ cuobjdump_parse(parser.scanner, &parser, cuobjdumpSectionList);
+ cuobjdump_lex_destroy(parser.scanner);
fclose(cuobjdump_in);
printf("Done parsing!!!\n");
} else {
@@ -2273,8 +2637,15 @@ void extract_code_using_cuobjdump(){
std::cout << "Done" << std::endl;
std::cout << "Trying to parse " << libcodfn.str() << std::endl;
+ FILE *cuobjdump_in;
cuobjdump_in = fopen(libcodfn.str().c_str(), "r");
- cuobjdump_parse();
+ struct cuobjdump_parser parser;
+ parser.elfserial = 1;
+ parser.ptxserial = 1;
+ cuobjdump_lex_init(&(parser.scanner));
+ cuobjdump_set_in(cuobjdump_in, (parser.scanner));
+ cuobjdump_parse(parser.scanner, &parser, cuobjdumpSectionList);
+ cuobjdump_lex_destroy(parser.scanner);
fclose(cuobjdump_in);
std::getline(libsf, line);
}
@@ -2324,7 +2695,7 @@ void printSectionList(std::list<cuobjdumpSection*> sl) {
}
//! Remove unecessary sm versions from the section list
-std::list<cuobjdumpSection*> pruneSectionList(std::list<cuobjdumpSection*> cuobjdumpSectionList, CUctx_st *context) {
+std::list<cuobjdumpSection*> cuda_runtime_api::pruneSectionList(CUctx_st *context) {
unsigned forced_max_capability = context->get_device()->get_gpgpu()->get_config().get_forced_max_capability();
//For ptxplus, force the max capability to 19 if it's higher or unspecified(0)
@@ -2377,7 +2748,7 @@ std::list<cuobjdumpSection*> pruneSectionList(std::list<cuobjdumpSection*> cuobj
}
//! Merge all PTX sections that have a specific identifier into one file
-std::list<cuobjdumpSection*> mergeMatchingSections(std::list<cuobjdumpSection*> cuobjdumpSectionList, std::string identifier){
+std::list<cuobjdumpSection*> cuda_runtime_api::mergeMatchingSections(std::string identifier){
const char *ptxcode = "";
std::list<cuobjdumpSection*>::iterator old_iter;
cuobjdumpPTXSection* old_ptxsection = NULL;
@@ -2420,7 +2791,7 @@ std::list<cuobjdumpSection*> mergeMatchingSections(std::list<cuobjdumpSection*>
}
//! Merge any PTX sections with matching identifiers
-std::list<cuobjdumpSection*> mergeSections(std::list<cuobjdumpSection*> cuobjdumpSectionList){
+std::list<cuobjdumpSection*> cuda_runtime_api::mergeSections(){
std::vector<std::string> identifier;
cuobjdumpPTXSection* ptxsection;
@@ -2442,7 +2813,7 @@ std::list<cuobjdumpSection*> mergeSections(std::list<cuobjdumpSection*> cuobjdum
for ( std::vector<std::string>::iterator iter = identifier.begin();
iter != identifier.end();
iter++) {
- cuobjdumpSectionList = mergeMatchingSections(cuobjdumpSectionList, *iter);
+ cuobjdumpSectionList = mergeMatchingSections(*iter);
}
return cuobjdumpSectionList;
@@ -2467,7 +2838,7 @@ cuobjdumpELFSection* findELFSectionInList(std::list<cuobjdumpSection*> sectionli
}
//! Find an ELF section in all the known lists
-cuobjdumpELFSection* findELFSection(const std::string identifier){
+cuobjdumpELFSection* cuda_runtime_api::findELFSection(const std::string identifier){
cuobjdumpELFSection* sec = findELFSectionInList(cuobjdumpSectionList, identifier);
if (sec!=NULL)return sec;
sec = findELFSectionInList(libSectionList, identifier);
@@ -2478,7 +2849,7 @@ cuobjdumpELFSection* findELFSection(const std::string identifier){
}
//! Within the section list, find the PTX section corresponding to a given identifier
-cuobjdumpPTXSection* findPTXSectionInList(std::list<cuobjdumpSection*> sectionlist, const std::string identifier){
+cuobjdumpPTXSection* cuda_runtime_api::findPTXSectionInList(std::list<cuobjdumpSection*> &sectionlist, const std::string identifier){
std::list<cuobjdumpSection*>::iterator iter;
for ( iter = sectionlist.begin();
iter != sectionlist.end();
@@ -2489,8 +2860,7 @@ cuobjdumpPTXSection* findPTXSectionInList(std::list<cuobjdumpSection*> sectionli
if(ptxsection->getIdentifier() == identifier)
return ptxsection;
else {
- extern bool g_cdp_enabled;
- if(g_cdp_enabled) {
+ if(gpgpu_ctx->device_runtime->g_cdp_enabled) {
printf("Warning: __cudaRegisterFatBinary needs %s, but find PTX section with %s\n",
identifier.c_str(), ptxsection->getIdentifier().c_str());
return ptxsection;
@@ -2502,7 +2872,7 @@ cuobjdumpPTXSection* findPTXSectionInList(std::list<cuobjdumpSection*> sectionli
}
//! Find an PTX section in all the known lists
-cuobjdumpPTXSection* findPTXSection(const std::string identifier){
+cuobjdumpPTXSection* cuda_runtime_api::findPTXSection(const std::string identifier){
cuobjdumpPTXSection* sec = findPTXSectionInList(cuobjdumpSectionList, identifier);
if (sec!=NULL)return sec;
sec = findPTXSectionInList(libSectionList, identifier);
@@ -2515,35 +2885,27 @@ cuobjdumpPTXSection* findPTXSection(const std::string identifier){
//! Extract the code using cuobjdump and remove unnecessary sections
-void cuobjdumpInit(){
+void cuda_runtime_api::cuobjdumpInit(){
CUctx_st *context = GPGPUSim_Context();
extract_code_using_cuobjdump(); //extract all the output of cuobjdump to _cuobjdump_*.*
const char* pre_load = getenv("CUOBJDUMP_SIM_FILE");
if (pre_load ==NULL || strlen(pre_load)==0){
- cuobjdumpSectionList = pruneSectionList(cuobjdumpSectionList, context);
- cuobjdumpSectionList = mergeSections(cuobjdumpSectionList);
+ cuobjdumpSectionList = pruneSectionList(context);
+ cuobjdumpSectionList = mergeSections();
}
}
-std::map<int, std::string> fatbinmap;
-std::map<int, bool>fatbin_registered;
-std::map<std::string, symbol_table*> name_symtab;
-
-//! Keep track of the association between filename and cubin handle
-void cuobjdumpRegisterFatBinary(unsigned int handle, const char* filename){
- fatbinmap[handle] = filename;
-}
//! Either submit PTX for simulation or convert SASS to PTXPlus and submit it
-void cuobjdumpParseBinary(unsigned int handle){
+void gpgpu_context::cuobjdumpParseBinary(unsigned int handle){
- if(fatbin_registered[handle]) return;
- fatbin_registered[handle] = true;
CUctx_st *context = GPGPUSim_Context();
- std::string fname = fatbinmap[handle];
+ if(api->fatbin_registered[handle]) return;
+ api->fatbin_registered[handle] = true;
+ std::string fname = api->fatbinmap[handle];
- if (name_symtab.find(fname) != name_symtab.end()) {
- symbol_table *symtab = name_symtab[fname];
+ if (api->name_symtab.find(fname) != api->name_symtab.end()) {
+ symbol_table *symtab = api->name_symtab[fname];
context->add_binary(symtab, handle);
return;
}
@@ -2552,7 +2914,7 @@ void cuobjdumpParseBinary(unsigned int handle){
#if (CUDART_VERSION >= 6000)
//loops through all ptx files from smallest sm version to largest
std::map<unsigned,std::set<std::string> >::iterator itr_m;
- for (itr_m = version_filename.begin(); itr_m!=version_filename.end(); itr_m++){
+ for (itr_m = api->version_filename.begin(); itr_m!=api->version_filename.end(); itr_m++){
std::set<std::string>::iterator itr_s;
for (itr_s = itr_m->second.begin(); itr_s!=itr_m->second.end(); itr_s++){
std::string ptx_filename = *itr_s;
@@ -2560,11 +2922,11 @@ void cuobjdumpParseBinary(unsigned int handle){
symtab = gpgpu_ptx_sim_load_ptx_from_filename( ptx_filename.c_str() );
}
}
- name_symtab[fname] = symtab;
+ api->name_symtab[fname] = symtab;
context->add_binary(symtab, handle);
- load_static_globals(symtab,STATIC_ALLOC_LIMIT,0xFFFFFFFF,context->get_device()->get_gpgpu());
- load_constants(symtab,STATIC_ALLOC_LIMIT,context->get_device()->get_gpgpu());
- for (itr_m = version_filename.begin(); itr_m!=version_filename.end(); itr_m++){
+ api->load_static_globals(symtab,STATIC_ALLOC_LIMIT,0xFFFFFFFF,context->get_device()->get_gpgpu());
+ api->load_constants(symtab,STATIC_ALLOC_LIMIT,context->get_device()->get_gpgpu());
+ for (itr_m = api->version_filename.begin(); itr_m!=api->version_filename.end(); itr_m++){
std::set<std::string>::iterator itr_s;
for (itr_s = itr_m->second.begin(); itr_s!=itr_m->second.end(); itr_s++){
std::string ptx_filename = *itr_s;
@@ -2576,8 +2938,8 @@ void cuobjdumpParseBinary(unsigned int handle){
#endif
unsigned max_capability = 0;
- for ( std::list<cuobjdumpSection*>::iterator iter = cuobjdumpSectionList.begin();
- iter != cuobjdumpSectionList.end();
+ for ( std::list<cuobjdumpSection*>::iterator iter = api->cuobjdumpSectionList.begin();
+ iter != api->cuobjdumpSectionList.end();
iter++){
unsigned capability = (*iter)->getArch();
if (capability > max_capability) max_capability = capability;
@@ -2588,7 +2950,7 @@ void cuobjdumpParseBinary(unsigned int handle){
cuobjdumpPTXSection* ptx = NULL;
const char* pre_load = getenv("CUOBJDUMP_SIM_FILE");
if(pre_load==NULL || strlen(pre_load)==0)
- ptx = findPTXSection(fname);
+ ptx = api->findPTXSection(fname);
char *ptxcode;
const char *override_ptx_name = getenv("PTX_SIM_KERNELFILE");
if (override_ptx_name == NULL or getenv("PTX_SIM_USE_PTX_FILE") == NULL or strlen(getenv("PTX_SIM_USE_PTX_FILE"))==0) {
@@ -2598,192 +2960,47 @@ void cuobjdumpParseBinary(unsigned int handle){
ptxcode = readfile(override_ptx_name);
}
if(context->get_device()->get_gpgpu()->get_config().convert_to_ptxplus() ) {
- cuobjdumpELFSection* elfsection = findELFSection(ptx->getIdentifier());
+ cuobjdumpELFSection* elfsection = api->findELFSection(ptx->getIdentifier());
assert (elfsection!= NULL);
- char *ptxplus_str = gpgpu_ptx_sim_convert_ptx_and_sass_to_ptxplus(
+ char *ptxplus_str = ptxinfo->gpgpu_ptx_sim_convert_ptx_and_sass_to_ptxplus(
ptx->getPTXfilename(),
elfsection->getELFfilename(),
elfsection->getSASSfilename());
symtab=gpgpu_ptx_sim_load_ptx_from_string(ptxplus_str, handle);
printf("Adding %s with cubin handle %u\n", ptx->getPTXfilename().c_str(), handle);
context->add_binary(symtab, handle);
- gpgpu_ptxinfo_load_from_string( ptxcode, handle, max_capability );
+ gpgpu_ptxinfo_load_from_string( ptxcode, handle, max_capability, context->no_of_ptx );
delete[] ptxplus_str;
} else {
symtab=gpgpu_ptx_sim_load_ptx_from_string(ptxcode, handle);
//if CUOBJDUMP_SIM_FILE is not set, ptx is NULL. So comment below.
//printf("Adding %s with cubin handle %u\n", ptx->getPTXfilename().c_str(), handle);
context->add_binary(symtab, handle);
- gpgpu_ptxinfo_load_from_string( ptxcode, handle, max_capability );
+ gpgpu_ptxinfo_load_from_string( ptxcode, handle, max_capability, context->no_of_ptx );
}
- load_static_globals(symtab,STATIC_ALLOC_LIMIT,0xFFFFFFFF,context->get_device()->get_gpgpu());
- load_constants(symtab,STATIC_ALLOC_LIMIT,context->get_device()->get_gpgpu());
- name_symtab[fname] = symtab;
+ api->load_static_globals(symtab,STATIC_ALLOC_LIMIT,0xFFFFFFFF,context->get_device()->get_gpgpu());
+ api->load_constants(symtab,STATIC_ALLOC_LIMIT,context->get_device()->get_gpgpu());
+ api->name_symtab[fname] = symtab;
//TODO: Remove temporarily files as per configurations
}
+}
+
+extern "C" {
void** CUDARTAPI __cudaRegisterFatBinary( void *fatCubin )
{
if(g_debug_execution >= 3){
announce_call(__my_func__);
}
-#if (CUDART_VERSION < 2010)
- printf("GPGPU-Sim PTX: ERROR ** this version of GPGPU-Sim requires CUDA 2.1 or higher\n");
- exit(1);
-#endif
- CUctx_st *context = GPGPUSim_Context();
- static unsigned next_fat_bin_handle = 1;
- if(context->get_device()->get_gpgpu()->get_config().use_cuobjdump()) {
- // The following workaround has only been verified on 64-bit systems.
- if (sizeof(void*) == 4)
- printf("GPGPU-Sim PTX: FatBin file name extraction has not been tested on 32-bit system.\n");
-
- // This code will get the CUDA version the app was compiled with.
- // We need this to determine how to handle the parsing of the binary.
- // Making this a runtime variable based on the app, enables GPGPU-Sim compiled
- // with a newer version of CUDA to run apps compiled with older versions of
- // CUDA. This is especially useful for PTXPLUS execution.
- //Skip cuda version check for pytorch application
- std::string app_binary_path = get_app_binary();
- int pos = app_binary_path.find("python");
- if (pos==std::string::npos){
- // Not pytorch app : checking cuda version
- int app_cuda_version = get_app_cuda_version();
- assert( app_cuda_version == CUDART_VERSION / 1000 && "The app must be compiled with same major version as the simulator." );
- }
-
- //int app_cuda_version = get_app_cuda_version();
- //assert( app_cuda_version == CUDART_VERSION / 1000 && "The app must be compiled with same major version as the simulator." );
- const char* filename;
-#if CUDART_VERSION < 6000
- // FatBin handle from the .fatbin.c file (one of the intermediate files generated by NVCC)
- typedef struct {int m; int v; const unsigned long long* d; char* f;} __fatDeviceText __attribute__ ((aligned (8)));
- __fatDeviceText * fatDeviceText = (__fatDeviceText *) fatCubin;
-
- // Extract the source code file name that generate the given FatBin.
- // - Obtains the pointer to the actual fatbin structure from the FatBin handle (fatCubin).
- // - An integer inside the fatbin structure contains the relative offset to the source code file name.
- // - This offset differs among different CUDA and GCC versions.
- char * pfatbin = (char*) fatDeviceText->d;
- int offset = *((int*)(pfatbin+48));
- filename = (pfatbin+16+offset);
-#else
- filename = "default";
-#endif
-
- // The extracted file name is associated with a fat_cubin_handle passed
- // into cudaLaunch(). Inside cudaLaunch(), the associated file name is
- // used to find the PTX/SASS section from cuobjdump, which contains the
- // PTX/SASS code for the launched kernel function.
- // This allows us to work around the fact that cuobjdump only outputs the
- // file name associated with each section.
- unsigned long long fat_cubin_handle = next_fat_bin_handle;
- next_fat_bin_handle++;
- printf("GPGPU-Sim PTX: __cudaRegisterFatBinary, fat_cubin_handle = %llu, filename=%s\n", fat_cubin_handle, filename);
- /*!
- * This function extracts all data from all files in first call
- * then for next calls, only returns the appropriate number
- */
- assert(fat_cubin_handle >= 1);
- if (fat_cubin_handle==1) cuobjdumpInit();
- cuobjdumpRegisterFatBinary(fat_cubin_handle, filename);
-
- return (void**)fat_cubin_handle;
- }
-#if (CUDART_VERSION < 8000)
- else {
- static unsigned source_num=1;
- unsigned long long fat_cubin_handle = next_fat_bin_handle++;
- __cudaFatCudaBinary *info = (__cudaFatCudaBinary *)fatCubin;
- assert( info->version >= 3 );
- unsigned num_ptx_versions=0;
- unsigned max_capability=0;
- unsigned selected_capability=0;
- bool found=false;
- unsigned forced_max_capability = context->get_device()->get_gpgpu()->get_config().get_forced_max_capability();
- if (!info->ptx){
- printf("ERROR: Cannot find ptx code in cubin file\n"
- "\tIf you are using CUDA 4.0 or higher, please enable -gpgpu_ptx_use_cuobjdump or downgrade to CUDA 3.1\n");
- exit(1);
- }
- while( info->ptx[num_ptx_versions].gpuProfileName != NULL ) {
- unsigned capability=0;
- sscanf(info->ptx[num_ptx_versions].gpuProfileName,"compute_%u",&capability);
- printf("GPGPU-Sim PTX: __cudaRegisterFatBinary found PTX versions for '%s', ", info->ident);
- printf("capability = %s\n", info->ptx[num_ptx_versions].gpuProfileName );
- if( forced_max_capability ) {
- if( capability > max_capability && capability <= forced_max_capability ) {
- found = true;
- max_capability=capability;
- selected_capability = num_ptx_versions;
- }
- } else {
- if( capability > max_capability ) {
- found = true;
- max_capability=capability;
- selected_capability = num_ptx_versions;
- }
- }
- num_ptx_versions++;
- }
- if( found ) {
- printf("GPGPU-Sim PTX: Loading PTX for %s, capability = %s\n",
- info->ident, info->ptx[selected_capability].gpuProfileName );
- symbol_table *symtab;
- const char *ptx = info->ptx[selected_capability].ptx;
- if(context->get_device()->get_gpgpu()->get_config().convert_to_ptxplus() ) {
- printf("GPGPU-Sim PTX: ERROR ** PTXPlus is only supported through cuobjdump\n"
- "\tEither enable cuobjdump or disable PTXPlus in your configuration file\n");
- exit(1);
- } else {
- symtab=gpgpu_ptx_sim_load_ptx_from_string(ptx,source_num);
- context->add_binary(symtab,fat_cubin_handle);
- gpgpu_ptxinfo_load_from_string( ptx, source_num, max_capability );
- }
- source_num++;
- load_static_globals(symtab,STATIC_ALLOC_LIMIT,0xFFFFFFFF,context->get_device()->get_gpgpu());
- load_constants(symtab,STATIC_ALLOC_LIMIT,context->get_device()->get_gpgpu());
- } else {
- printf("GPGPU-Sim PTX: warning -- did not find an appropriate PTX in cubin\n");
- }
- return (void**)fat_cubin_handle;
- }
-#else
- else {
- printf("ERROR ** __cudaRegisterFatBinary() needs to be updated\n");
- abort();
- }
-#endif
+ return cudaRegisterFatBinaryInternal(fatCubin);
}
-void __cudaUnregisterFatBinary(void **fatCubinHandle)
+void CUDARTAPI __cudaRegisterFatBinaryEnd( void **fatCubinHandle )
{
if(g_debug_execution >= 3){
announce_call(__my_func__);
}
- ;
-}
-
-cudaError_t cudaDeviceReset ( void ) {
- // Should reset the simulated GPU
- if(g_debug_execution >= 3){
- announce_call(__my_func__);
- }
- return g_last_cudaError = cudaSuccess;
-}
-cudaError_t CUDARTAPI cudaDeviceSynchronize(void){
- if(g_debug_execution >= 3){
- announce_call(__my_func__);
- }
- //Blocks until the device has completed all preceding requested tasks
- synchronize();
- return g_last_cudaError = cudaSuccess;
-}
-
-void CUDARTAPI __cudaRegisterFatBinaryEnd( void **fatCubinHandle )
-{
-
}
unsigned CUDARTAPI __cudaPushCallConfiguration(dim3 gridDim,
@@ -2791,7 +3008,10 @@ unsigned CUDARTAPI __cudaPushCallConfiguration(dim3 gridDim,
size_t sharedMem = 0,
struct CUstream_st *stream = 0)
{
-
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ cudaConfigureCallInternal(gridDim, blockDim, sharedMem, stream);
}
cudaError_t CUDARTAPI __cudaPopCallConfiguration(
@@ -2801,9 +3021,13 @@ cudaError_t CUDARTAPI __cudaPopCallConfiguration(
void *stream
)
{
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
return g_last_cudaError = cudaSuccess;
}
+
void CUDARTAPI __cudaRegisterFunction(
void **fatCubinHandle,
const char *hostFun,
@@ -2814,18 +3038,19 @@ void CUDARTAPI __cudaRegisterFunction(
uint3 *bid,
dim3 *bDim,
dim3 *gDim
-)
-{
- if(g_debug_execution >= 3){
- announce_call(__my_func__);
- }
- CUctx_st *context = GPGPUSim_Context();
- unsigned fat_cubin_handle = (unsigned)(unsigned long long)fatCubinHandle;
- printf("GPGPU-Sim PTX: __cudaRegisterFunction %s : hostFun 0x%p, fat_cubin_handle = %u\n",
- deviceFun, hostFun, fat_cubin_handle);
- if(context->get_device()->get_gpgpu()->get_config().use_cuobjdump())
- cuobjdumpParseBinary(fat_cubin_handle);
- context->register_function( fat_cubin_handle, hostFun, deviceFun );
+) {
+ cudaRegisterFunctionInternal(
+ fatCubinHandle,
+ hostFun,
+ deviceFun,
+ deviceName,
+ thread_limit,
+ tid,
+ bid,
+ bDim,
+ gDim
+ );
+
}
extern void __cudaRegisterVar(
@@ -2838,19 +3063,43 @@ extern void __cudaRegisterVar(
int constant,
int global )
{
+ cudaRegisterVarInternal(
+ fatCubinHandle,
+ hostVar,
+ deviceAddress,
+ deviceName,
+ ext,
+ size,
+ constant,
+ global );
+}
+
+__host__ cudaError_t CUDARTAPI cudaConfigureCall(dim3 gridDim, dim3 blockDim, size_t sharedMem, cudaStream_t stream)
+{
+ return cudaConfigureCallInternal(gridDim, blockDim, sharedMem, stream);
+}
+
+void __cudaUnregisterFatBinary(void **fatCubinHandle)
+{
if(g_debug_execution >= 3){
announce_call(__my_func__);
}
- printf("GPGPU-Sim PTX: __cudaRegisterVar: hostVar = %p; deviceAddress = %s; deviceName = %s\n", hostVar, deviceAddress, deviceName);
- printf("GPGPU-Sim PTX: __cudaRegisterVar: Registering const memory space of %d bytes\n", size);
- if(GPGPUSim_Context()->get_device()->get_gpgpu()->get_config().use_cuobjdump())
- cuobjdumpParseBinary((unsigned)(unsigned long long)fatCubinHandle);
- fflush(stdout);
- if ( constant && !global && !ext ) {
- gpgpu_ptx_sim_register_const_variable(hostVar,deviceName,size);
- } else if ( !constant && !global && !ext ) {
- gpgpu_ptx_sim_register_global_variable(hostVar,deviceName,size);
- } else cuda_not_implemented(__my_func__,__LINE__);
+}
+
+cudaError_t cudaDeviceReset ( void ) {
+ // Should reset the simulated GPU
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ return g_last_cudaError = cudaSuccess;
+}
+cudaError_t CUDARTAPI cudaDeviceSynchronize(void){
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ //Blocks until the device has completed all preceding requested tasks
+ synchronize();
+ return g_last_cudaError = cudaSuccess;
}
@@ -2922,10 +3171,6 @@ char __cudaInitModule(
}
-#ifndef OPENGL_SUPPORT
-typedef unsigned long GLuint;
-#endif
-
cudaError_t cudaGLRegisterBufferObject(GLuint bufferObj)
{
if(g_debug_execution >= 3){
@@ -2935,70 +3180,9 @@ cudaError_t cudaGLRegisterBufferObject(GLuint bufferObj)
return g_last_cudaError = cudaSuccess;
}
-struct glbmap_entry {
- GLuint m_bufferObj;
- void *m_devPtr;
- size_t m_size;
- struct glbmap_entry *m_next;
-};
-typedef struct glbmap_entry glbmap_entry_t;
-
-glbmap_entry_t* g_glbmap = NULL;
-
cudaError_t cudaGLMapBufferObject(void** devPtr, GLuint bufferObj)
{
- if(g_debug_execution >= 3){
- announce_call(__my_func__);
- }
-#ifdef OPENGL_SUPPORT
- GLint buffer_size=0;
- CUctx_st* ctx = GPGPUSim_Context();
-
- glbmap_entry_t *p = g_glbmap;
- while ( p && p->m_bufferObj != bufferObj )
- p = p->m_next;
- if ( p == NULL ) {
- glBindBuffer(GL_ARRAY_BUFFER,bufferObj);
- glGetBufferParameteriv(GL_ARRAY_BUFFER,GL_BUFFER_SIZE,&buffer_size);
- assert( buffer_size != 0 );
- *devPtr = ctx->get_device()->get_gpgpu()->gpu_malloc(buffer_size);
-
- // create entry and insert to front of list
- glbmap_entry_t *n = (glbmap_entry_t *) calloc(1,sizeof(glbmap_entry_t));
- n->m_next = g_glbmap;
- g_glbmap = n;
-
- // initialize entry
- n->m_bufferObj = bufferObj;
- n->m_devPtr = *devPtr;
- n->m_size = buffer_size;
-
- p = n;
- } else {
- buffer_size = p->m_size;
- *devPtr = p->m_devPtr;
- }
-
- if ( *devPtr ) {
- char *data = (char *) calloc(p->m_size,1);
- glGetBufferSubData(GL_ARRAY_BUFFER,0,buffer_size,data);
- memcpy_to_gpu( (size_t) *devPtr, data, buffer_size );
- free(data);
- printf("GPGPU-Sim PTX: cudaGLMapBufferObject %zu bytes starting at 0x%llx..\n", (size_t)buffer_size,
- (unsigned long long) *devPtr);
- return g_last_cudaError = cudaSuccess;
- } else {
- return g_last_cudaError = cudaErrorMemoryAllocation;
- }
-
- return g_last_cudaError = cudaSuccess;
-#else
- fflush(stdout);
- fflush(stderr);
- printf("GPGPU-Sim PTX: GPGPU-Sim support for OpenGL integration disabled -- exiting\n");
- fflush(stdout);
- exit(50);
-#endif
+ return cudaGLMapBufferObjectInternal(devPtr, bufferObj);
}
cudaError_t cudaGLUnmapBufferObject(GLuint bufferObj)
@@ -3007,7 +3191,8 @@ cudaError_t cudaGLUnmapBufferObject(GLuint bufferObj)
announce_call(__my_func__);
}
#ifdef OPENGL_SUPPORT
- glbmap_entry_t *p = g_glbmap;
+ CUctx_st* ctx = GPGPUSim_Context();
+ glbmap_entry_t *p = ctx->api->g_glbmap;
while ( p && p->m_bufferObj != bufferObj )
p = p->m_next;
if ( p == NULL )
@@ -3041,45 +3226,12 @@ cudaError_t cudaGLUnregisterBufferObject(GLuint bufferObj)
cudaError_t CUDARTAPI cudaHostAlloc(void **pHost, size_t bytes, unsigned int flags)
{
- if(g_debug_execution >= 3){
- announce_call(__my_func__);
- }
- *pHost = malloc(bytes);
- //need to track the size allocated so that cudaHostGetDevicePointer() can function properly.
- //TODO: vary this function behavior based on flags value (following nvidia documentation)
- pinned_memory_size[*pHost]=bytes;
- if( *pHost )
- return g_last_cudaError = cudaSuccess;
- else
- return g_last_cudaError = cudaErrorMemoryAllocation;
+ return cudaHostAllocInternal(pHost, bytes, flags);
}
cudaError_t CUDARTAPI cudaHostGetDevicePointer(void **pDevice, void *pHost, unsigned int flags)
{
- if(g_debug_execution >= 3){
- announce_call(__my_func__);
- }
- //only cpu memory allocation happens in cudaHostAlloc. Linking with device pointer to pinned memory happens here.
- //TODO: once kernel is executed, the contents in global pointer of GPU must be copied back to CPU host pointer!
- flags=0;
- CUctx_st* context = GPGPUSim_Context();
- gpgpu_t *gpu = context->get_device()->get_gpgpu();
- std::map<void *, size_t>::const_iterator i = pinned_memory_size.find(pHost);
- assert(i != pinned_memory_size.end());
- size_t size = i->second;
- *pDevice = gpu->gpu_malloc(size);
- if(g_debug_execution >= 3){
- printf("GPGPU-Sim PTX: cudaMallocing %zu bytes starting at 0x%llx..\n",size, (unsigned long long) *pDevice);
- g_mallocPtr_Size[(unsigned long long)*pDevice] = size;
- }
- if ( *pDevice ) {
- pinned_memory[pHost]=pDevice;
- //Copy contents in cpu to gpu
- gpu->memcpy_to_gpu((size_t)*pDevice,pHost,size);
- return g_last_cudaError = cudaSuccess;
- } else {
- return g_last_cudaError = cudaErrorMemoryAllocation;
- }
+ return cudaHostGetDevicePointerInternal(pDevice, pHost, flags);
}
__host__ cudaError_t CUDARTAPI cudaPointerGetAttributes(
@@ -3143,61 +3295,12 @@ cudaError_t CUDARTAPI cudaSetDeviceFlags( int flags )
}
}
-size_t getMaxThreadsPerBlock(struct cudaFuncAttributes *attr) {
- _cuda_device_id *dev = GPGPUSim_Init();
- struct cudaDeviceProp prop;
-
- prop = *dev->get_prop();
-
- size_t max = prop.maxThreadsPerBlock;
-
- if (attr->numRegs && (prop.regsPerBlock / attr->numRegs) < max)
- max = prop.regsPerBlock / attr->numRegs;
- if (attr->sharedSizeBytes && (prop.sharedMemPerBlock / attr->sharedSizeBytes) < max)
- max = prop.sharedMemPerBlock / attr->sharedSizeBytes;
- return max;
-}
cudaError_t CUDARTAPI cudaFuncGetAttributes(struct cudaFuncAttributes *attr, const char *hostFun )
{
- if(g_debug_execution >= 3){
- announce_call(__my_func__);
- }
- CUctx_st *context = GPGPUSim_Context();
- function_info *entry = context->get_kernel(hostFun);
- if( entry ) {
- const struct gpgpu_ptx_sim_info *kinfo = entry->get_kernel_info();
- attr->sharedSizeBytes = kinfo->smem;
- attr->constSizeBytes = kinfo->cmem;
- attr->localSizeBytes = kinfo->lmem;
- attr->numRegs = kinfo->regs;
- if(kinfo->maxthreads > 0)
- attr->maxThreadsPerBlock = kinfo->maxthreads;
- else
- attr->maxThreadsPerBlock = getMaxThreadsPerBlock(attr);
-#if CUDART_VERSION >= 3000
- attr->ptxVersion = kinfo->ptx_version;
- attr->binaryVersion = kinfo->sm_target;
-#endif
- }
- return g_last_cudaError = cudaSuccess;
-}
-
-cudaError_t CUDARTAPI cudaEventCreateWithFlags(cudaEvent_t *event, int flags)
-{
- if(g_debug_execution >= 3){
- announce_call(__my_func__);
- }
- CUevent_st *e = new CUevent_st(flags==cudaEventBlockingSync);
- g_timer_events[e->get_uid()] = e;
-#if CUDART_VERSION >= 3000
- *event = e;
-#else
- *event = e->get_uid();
-#endif
- return g_last_cudaError = cudaSuccess;
+ return cudaFuncGetAttributesInternal(attr, hostFun );
}
cudaError_t CUDARTAPI cudaDriverGetVersion(int *driverVersion)
@@ -3237,26 +3340,64 @@ __host__ cudaError_t CUDARTAPI cudaDeviceSetLimit(enum cudaLimit limit, size_t v
return g_last_cudaError = cudaSuccess;
}
-#if CUDART_VERSION >= 9000
-__host__ cudaError_t cudaFuncSetAttribute ( const void* func, enum cudaFuncAttribute attr, int value ) {
+//#if CUDART_VERSION >= 9000
+//__host__ cudaError_t cudaFuncSetAttribute ( const void* func, enum cudaFuncAttribute attr, int value ) {
//ignore this Attribute for now, and the default is that carveout = cudaSharedmemCarveoutDefault; // (-1)
- return g_last_cudaError = cudaSuccess;
-}
+// return g_last_cudaError = cudaSuccess;
+//}
-#if CUDART_VERSION >= 9020
-__host__ __device__ unsigned __cudaPushCallConfiguration(dim3 gridDim, dim3 blockDim,
- size_t sharedMem = 0,
- void *stream = 0) {
- return 1;
-}
#endif
#endif
#endif
+
+#if CUDART_VERSION >= 9000
+/**
+ * \brief Set attributes for a given function
+ *
+ * This function sets the attributes of a function specified via \p entry.
+ * The parameter \p entry must be a pointer to a function that executes
+ * on the device. The parameter specified by \p entry must be declared as a \p __global__
+ * function. The enumeration defined by \p attr is set to the value defined by \p value
+ * If the specified function does not exist, then ::cudaErrorInvalidDeviceFunction is returned.
+ * If the specified attribute cannot be written, or if the value is incorrect,
+ * then ::cudaErrorInvalidValue is returned.
+ *
+ * Valid values for \p attr are:
+ * ::cuFuncAttrMaxDynamicSharedMem - Maximum size of dynamic shared memory per block
+ * ::cudaFuncAttributePreferredSharedMemoryCarveout - Preferred shared memory-L1 cache split ratio
+ *
+ * \param entry - Function to get attributes of
+ * \param attr - Attribute to set
+ * \param value - Value to set
+ *
+ * \return
+ * ::cudaSuccess,
+ * ::cudaErrorInitializationError,
+ * ::cudaErrorInvalidDeviceFunction,
+ * ::cudaErrorInvalidValue
+ * \notefnerr
+ *
+ * \ref ::cudaLaunchKernel(const T *func, dim3 gridDim, dim3 blockDim, void **args, size_t sharedMem, cudaStream_t stream) "cudaLaunchKernel (C++ API)",
+ * \ref ::cudaFuncSetCacheConfig(T*, enum cudaFuncCache) "cudaFuncSetCacheConfig (C++ API)",
+ * \ref ::cudaFuncGetAttributes(struct cudaFuncAttributes*, const void*) "cudaFuncGetAttributes (C API)",
+ * ::cudaSetDoubleForDevice,
+ * ::cudaSetDoubleForHost,
+ * \ref ::cudaSetupArgument(T, size_t) "cudaSetupArgument (C++ API)"
+ */
+cudaError_t CUDARTAPI cudaFuncSetAttribute(const void *func, enum cudaFuncAttribute attr, int value)
+{
+ if(g_debug_execution >= 3){
+ announce_call(__my_func__);
+ }
+ printf("GPGPU-Sim PTX: Execution warning: ignoring call to \"%s ( func=%p, attr=%d, value=%d )\"\n",
+ __my_func__, func, attr, value );
+ return g_last_cudaError = cudaSuccess;
+}
#endif
cudaError_t CUDARTAPI cudaGLSetGLDevice(int device)
@@ -3328,17 +3469,9 @@ int CUDARTAPI __cudaSynchronizeThreads(void**, void*)
////////
-extern int ptx_parse();
-extern int ptx__scan_string(const char*);
-extern FILE *ptx_in;
-
-extern int ptxinfo_parse();
-extern int ptxinfo_debug;
-extern FILE *ptxinfo_in;
-
/// static functions
-static int load_static_globals( symbol_table *symtab, unsigned min_gaddr, unsigned max_gaddr, gpgpu_t *gpu )
+int cuda_runtime_api::load_static_globals( symbol_table *symtab, unsigned min_gaddr, unsigned max_gaddr, gpgpu_t *gpu )
{
if(g_debug_execution >= 3){
announce_call(__my_func__);
@@ -3377,7 +3510,7 @@ static int load_static_globals( symbol_table *symtab, unsigned min_gaddr, unsign
return ng_bytes;
}
-static int load_constants( symbol_table *symtab, addr_t min_gaddr, gpgpu_t *gpu )
+int cuda_runtime_api::load_constants( symbol_table *symtab, addr_t min_gaddr, gpgpu_t *gpu )
{
if(g_debug_execution >= 3){
announce_call(__my_func__);
@@ -3423,7 +3556,7 @@ static int load_constants( symbol_table *symtab, addr_t min_gaddr, gpgpu_t *gpu
return nc_bytes;
}
-kernel_info_t *gpgpu_cuda_ptx_sim_init_grid( const char *hostFun,
+kernel_info_t * cuda_runtime_api::gpgpu_cuda_ptx_sim_init_grid( const char *hostFun,
gpgpu_ptx_sim_arg_list_t args,
struct dim3 gridDim,
struct dim3 blockDim,
@@ -3451,7 +3584,7 @@ kernel_info_t *gpgpu_cuda_ptx_sim_init_grid( const char *hostFun,
}
entry->finalize(result->get_param_memory());
- g_ptx_kernel_count++;
+ gpgpu_ctx->func_sim->g_ptx_kernel_count++;
fflush(stdout);
if(g_debug_execution >= 4){
@@ -3919,33 +4052,8 @@ CUresult CUDAAPI
cuLinkAddFile(CUlinkState state, CUjitInputType type, const char *path,
unsigned int numOptions, CUjit_option *options, void **optionValues)
{
- if(g_debug_execution >= 3){
- announce_call(__my_func__);
- }
- static bool addedFile = false;
- if (addedFile){
- printf("GPGPU-Sim PTX: ERROR: cuLinkAddFile does not support multiple files\n");
- abort();
- }
-
- //blocking
- assert(type==CU_JIT_INPUT_PTX);
- CUctx_st *context = GPGPUSim_Context();
- char *file = getenv("PTX_JIT_PATH");
- if(file==NULL){
- printf("GPGPU-Sim PTX: ERROR: PTX_JIT_PATH has not been set\n");
- abort();
- }
- strcat(file,"/");
- strcat(file,path);
- symbol_table *symtab = gpgpu_ptx_sim_load_ptx_from_filename( file );
- std::string fname(path);
- name_symtab[fname] = symtab;
- context->add_binary(symtab, 1);
- load_static_globals(symtab,STATIC_ALLOC_LIMIT,0xFFFFFFFF,context->get_device()->get_gpgpu());
- load_constants(symtab,STATIC_ALLOC_LIMIT,context->get_device()->get_gpgpu());
- addedFile = true;
- return CUDA_SUCCESS;
+ return cuLinkAddFileInternal(state, type, path,
+ numOptions, options, optionValues);
}
#endif
@@ -4939,12 +5047,12 @@ CUresult CUDAAPI cuLaunchKernel(CUfunction f,
const char *hostFun = (const char*) f;
CUctx_st *context = GPGPUSim_Context();
function_info *entry = context->get_kernel(hostFun);
- cudaConfigureCall(dim3(gridDimX, gridDimY, gridDimZ), dim3(blockDimX, blockDimY, blockDimZ), sharedMemBytes, (cudaStream_t) hStream);
+ cudaConfigureCallInternal(dim3(gridDimX, gridDimY, gridDimZ), dim3(blockDimX, blockDimY, blockDimZ), sharedMemBytes, (cudaStream_t) hStream);
for(unsigned i = 0; i < entry->num_args(); i++){
std::pair<size_t, unsigned> p = entry->get_param_config(i);
cudaSetupArgument(kernelParams[i], p.first, p.second);
}
- cudaLaunch(hostFun);
+ cudaLaunchInternal(hostFun);
return CUDA_SUCCESS;
}
#endif /* CUDART_VERSION >= 4000 */
diff --git a/libcuda/cuobjdump.h b/libcuda/cuobjdump.h
new file mode 100644
index 0000000..6ab6778
--- /dev/null
+++ b/libcuda/cuobjdump.h
@@ -0,0 +1,80 @@
+#ifndef __cuobjdump_h__
+#define __cuobjdump_h__
+#include <string>
+#include <list>
+#include <iostream>
+
+typedef void * yyscan_t;
+struct cuobjdump_parser {
+ yyscan_t scanner;
+ int elfserial;
+ int ptxserial;
+ FILE *ptxfile;
+ FILE *elffile;
+ FILE *sassfile;
+ char filename [1024];
+};
+
+class cuobjdumpSection {
+public:
+ //Constructor
+ cuobjdumpSection() {
+ arch = 0;
+ identifier = "";
+ }
+ virtual ~cuobjdumpSection() {}
+ unsigned getArch() {return arch;}
+ void setArch(unsigned a) {arch = a;}
+ std::string getIdentifier() {return identifier;}
+ void setIdentifier(std::string i) {identifier = i;}
+ virtual void print(){std::cout << "cuobjdump Section: unknown type" << std::endl;}
+private:
+ unsigned arch;
+ std::string identifier;
+};
+
+class cuobjdumpELFSection : public cuobjdumpSection
+{
+public:
+ cuobjdumpELFSection() {}
+ virtual ~cuobjdumpELFSection() {
+ elffilename = "";
+ sassfilename = "";
+ }
+ std::string getELFfilename() {return elffilename;}
+ void setELFfilename(std::string f) {elffilename = f;}
+ std::string getSASSfilename() {return sassfilename;}
+ void setSASSfilename(std::string f) {sassfilename = f;}
+ virtual void print() {
+ std::cout << "ELF Section:" << std::endl;
+ std::cout << "arch: sm_" << getArch() << std::endl;
+ std::cout << "identifier: " << getIdentifier() << std::endl;
+ std::cout << "elf filename: " << getELFfilename() << std::endl;
+ std::cout << "sass filename: " << getSASSfilename() << std::endl;
+ std::cout << std::endl;
+ }
+private:
+ std::string elffilename;
+ std::string sassfilename;
+};
+
+class cuobjdumpPTXSection : public cuobjdumpSection
+{
+public:
+ cuobjdumpPTXSection(){
+ ptxfilename = "";
+ }
+ std::string getPTXfilename() {return ptxfilename;}
+ void setPTXfilename(std::string f) {ptxfilename = f;}
+ virtual void print() {
+ std::cout << "PTX Section:" << std::endl;
+ std::cout << "arch: sm_" << getArch() << std::endl;
+ std::cout << "identifier: " << getIdentifier() << std::endl;
+ std::cout << "ptx filename: " << getPTXfilename() << std::endl;
+ std::cout << std::endl;
+ }
+private:
+ std::string ptxfilename;
+};
+
+#endif /* __cuobjdump_h__ */
diff --git a/libcuda/cuobjdump.l b/libcuda/cuobjdump.l
index 2b0dac8..5a19d65 100644
--- a/libcuda/cuobjdump.l
+++ b/libcuda/cuobjdump.l
@@ -30,6 +30,7 @@
%{
#include <stdio.h>
#include <string.h>
+#include "cuobjdump.h"
#include "cuobjdump_parser.h"
#define YY_NEVER_INTERACTIVE 1
@@ -38,9 +39,9 @@
#define YYDEBUG 1
-#define yylval cuobjdump_lval
-
-void cuobjdump_error(const char*);
+void cuobjdump_error(yyscan_t yyscanner, struct cuobjdump_parser* parser, std::list<cuobjdumpSection*> &cuobjdumpSectionList, const char* msg);
+#define YY_DECL int cuobjdump_lex \
+ (YYSTYPE * yylval_param , yyscan_t yyscanner, struct cuobjdump_parser* parser, std::list<cuobjdumpSection*> &cuobjdumpSectionList)
%}
%option stack
@@ -48,6 +49,8 @@ void cuobjdump_error(const char*);
%option yylineno
%option nounput
+%option bison-bridge
+%option reentrant
%s ptxcode
%s sasscode
@@ -69,54 +72,54 @@ newlines {newline}+
"ptxasOptions"{notnewline}*{newline}
-[1-9]{numeric}* yylval.string_value = strdup(yytext); return DECIMAL;
+[1-9]{numeric}* yylval->string_value = strdup(yytext); return DECIMAL;
"has debug info"{newline}
"Fatbin ptx code:"{newline} {
- yy_push_state(ptxcode);
- yy_push_state(identifier);
- yy_push_state(ptxheader);
- yylval.string_value = strdup(yytext);
+ yy_push_state(ptxcode, yyscanner);
+ yy_push_state(identifier, yyscanner);
+ yy_push_state(ptxheader, yyscanner);
+ yylval->string_value = strdup(yytext);
return PTXHEADER;
}
"Fatbin elf code:"{newline} {
- yy_push_state(elfcode);
- yy_push_state(identifier);
- yy_push_state(elfheader);
- yylval.string_value = strdup(yytext);
+ yy_push_state(elfcode, yyscanner);
+ yy_push_state(identifier, yyscanner);
+ yy_push_state(elfheader, yyscanner);
+ yylval->string_value = strdup(yytext);
return ELFHEADER;
}
/*PTX code tokens*/
-<ptxcode>{notnewline}*{newline} yylval.string_value = strdup(yytext); return PTXLINE;
+<ptxcode>{notnewline}*{newline} yylval->string_value = strdup(yytext); return PTXLINE;
/*ELF code tokens*/
<elfcode>{whitespace}*"code for sm_"{numeric}+{newline} {
BEGIN(sasscode);
- yylval.string_value = strdup(yytext);
+ yylval->string_value = strdup(yytext);
return SASSLINE;
}
-<elfcode>{notnewline}*{newline} yylval.string_value = strdup(yytext); return ELFLINE;
+<elfcode>{notnewline}*{newline} yylval->string_value = strdup(yytext); return ELFLINE;
/*SASS code tokens*/
-<sasscode>{notnewline}*{newline} yylval.string_value = strdup(yytext); return SASSLINE;
+<sasscode>{notnewline}*{newline} yylval->string_value = strdup(yytext); return SASSLINE;
<identifier>{newline}"compressed"{newline} BEGIN(conidentifier); return H_COMPRESSED;
<identifier>{newline}"identifier = " BEGIN(endidentifier); return H_IDENTIFIER;
-<identifier>{newline}{newline} yy_pop_state();
+<identifier>{newline}{newline} yy_pop_state(yyscanner);
<conidentifier>"identifier = " BEGIN(endidentifier); return H_IDENTIFIER;
-<conidentifier>{newline} yy_pop_state();
+<conidentifier>{newline} yy_pop_state(yyscanner);
-<endidentifier>{notnewline}+ yylval.string_value = strdup(yytext); yy_pop_state(); return FILENAME;
+<endidentifier>{notnewline}+ yylval->string_value = strdup(yytext); yy_pop_state(yyscanner); return FILENAME;
/*Header tokens*/
-<elfheader>[[:alnum:]_]+ yylval.string_value = strdup(yytext); return IDENTIFIER;
+<elfheader>[[:alnum:]_]+ yylval->string_value = strdup(yytext); return IDENTIFIER;
<elfheader>"================" return H_SEPARATOR;
<elfheader>"arch = " return H_ARCH;
<elfheader>"code version = " return H_CODEVERSION;
@@ -128,7 +131,7 @@ newlines {newline}+
/*Header tokens*/
-<ptxheader>[[:alnum:]_]+ yylval.string_value = strdup(yytext); return IDENTIFIER;
+<ptxheader>[[:alnum:]_]+ yylval->string_value = strdup(yytext); return IDENTIFIER;
<ptxheader>"================" return H_SEPARATOR;
<ptxheader>"arch = " return H_ARCH;
<ptxheader>"code version = " return H_CODEVERSION;
@@ -143,7 +146,7 @@ newlines {newline}+
/* Looking for the identifier (filename) then the header is done */
-<endheader>{notnewline}+ yylval.string_value = strdup(yytext); yy_pop_state(); return IDENTIFIER;
+<endheader>{notnewline}+ yylval->string_value = strdup(yytext); yy_pop_state(yyscanner); return IDENTIFIER;
@@ -153,11 +156,12 @@ newlines {newline}+
<<EOF>> BEGIN(INITIAL);return 0;
/*No other rule matched. Throw an error*/
-. cuobjdump_error("Invalid token");
+. cuobjdump_error(yyscanner, parser, cuobjdumpSectionList, "Invalid token");
%%
-void cuobjdump_error(const char* message)
+void cuobjdump_error(yyscan_t yyscanner, struct cuobjdump_parser* parser, std::list<cuobjdumpSection*> &cuobjdumpSectionList, const char* msg)
{
- printf(" %s near \"%s\"",message, yytext);
- printf(" on line %i\n",yylineno);
+ struct yyguts_t * yyg = (struct yyguts_t*)yyscanner;
+ printf(" %s near \"%s\"",msg, yytext);
+ printf(" on line %i\n",yylineno);
}
diff --git a/libcuda/cuobjdump.y b/libcuda/cuobjdump.y
index 31760f7..8d1bca6 100644
--- a/libcuda/cuobjdump.y
+++ b/libcuda/cuobjdump.y
@@ -29,24 +29,31 @@
%{
#include <stdio.h>
-int yylex(void);
-void yyerror(const char*);
-extern void addCuobjdumpSection(int sectiontype);
-void setCuobjdumparch(const char* arch);
-void setCuobjdumpidentifier(const char* identifier);
-void setCuobjdumpptxfilename(const char* filename);
-void setCuobjdumpelffilename(const char* filename);
-void setCuobjdumpsassfilename(const char* filename);
-int elfserial = 1;
-int ptxserial = 1;
-FILE *ptxfile;
-FILE *elffile;
-FILE *sassfile;
-char filename [1024];
+typedef void * yyscan_t;
+#include "cuobjdump.h"
+
+extern void addCuobjdumpSection(int sectiontype, std::list<cuobjdumpSection*> &cuobjdumpSectionList);
+void setCuobjdumparch(const char* arch, std::list<cuobjdumpSection*> &cuobjdumpSectionList);
+void setCuobjdumpidentifier(const char* identifier, std::list<cuobjdumpSection*> &cuobjdumpSectionList);
+void setCuobjdumpptxfilename(const char* filename, std::list<cuobjdumpSection*> &cuobjdumpSectionList);
+void setCuobjdumpelffilename(const char* filename, std::list<cuobjdumpSection*> &cuobjdumpSectionList);
+void setCuobjdumpsassfilename(const char* filename, std::list<cuobjdumpSection*> &cuobjdumpSectionList);
%}
+%define api.pure full
+%parse-param {yyscan_t scanner}
+%parse-param {struct cuobjdump_parser* parser}
+%parse-param {std::list<cuobjdumpSection*> &cuobjdumpSectionList}
+%lex-param {yyscan_t scanner}
+%lex-param {struct cuobjdump_parser* parser}
+%lex-param {std::list<cuobjdumpSection*> &cuobjdumpSectionList}
+
%union {
char* string_value;
}
+%{
+int yylex(YYSTYPE * yylval_param, yyscan_t yyscanner, struct cuobjdump_parser* parser, std::list<cuobjdumpSection*> &cuobjdumpSectionList);
+void yyerror(yyscan_t yyscanner, struct cuobjdump_parser* parser, std::list<cuobjdumpSection*> &cuobjdumpSectionList, const char* msg);
+%}
%token <string_value> H_SEPARATOR H_ARCH H_CODEVERSION H_PRODUCER H_HOST H_COMPILESIZE H_IDENTIFIER H_UNKNOWN H_COMPRESSED
%token <string_value> CODEVERSION
%token <string_value> STRING
@@ -70,25 +77,25 @@ emptylines : emptylines NEWLINE
| ;
section : PTXHEADER {
- addCuobjdumpSection(0);
- snprintf(filename, 1024, "_cuobjdump_%d.ptx", ptxserial++);
- ptxfile = fopen(filename, "w");
- setCuobjdumpptxfilename(filename);
+ addCuobjdumpSection(0, cuobjdumpSectionList);
+ snprintf(parser->filename, 1024, "_cuobjdump_%d.ptx", parser->ptxserial++);
+ parser->ptxfile = fopen(parser->filename, "w");
+ setCuobjdumpptxfilename(parser->filename, cuobjdumpSectionList);
} headerinfo compressedkeyword identifier ptxcode {
- fclose(ptxfile);
+ fclose(parser->ptxfile);
}
| ELFHEADER {
- addCuobjdumpSection(1);
- snprintf(filename, 1024, "_cuobjdump_%d.elf", elfserial);
- elffile = fopen(filename, "w");
- setCuobjdumpelffilename(filename);
+ addCuobjdumpSection(1, cuobjdumpSectionList);
+ snprintf(parser->filename, 1024, "_cuobjdump_%d.elf", parser->elfserial);
+ parser->elffile = fopen(parser->filename, "w");
+ setCuobjdumpelffilename(parser->filename, cuobjdumpSectionList);
} headerinfo compressedkeyword identifier elfcode {
- fclose(elffile);
- snprintf(filename, 1024, "_cuobjdump_%d.sass", elfserial++);
- sassfile = fopen(filename, "w");
- setCuobjdumpsassfilename(filename);
+ fclose(parser->elffile);
+ snprintf(parser->filename, 1024, "_cuobjdump_%d.sass", parser->elfserial++);
+ parser->sassfile = fopen(parser->filename, "w");
+ setCuobjdumpsassfilename(parser->filename, cuobjdumpSectionList);
} sasscode {
- fclose(sassfile);
+ fclose(parser->sassfile);
};
headerinfo : H_SEPARATOR NEWLINE
@@ -96,27 +103,27 @@ headerinfo : H_SEPARATOR NEWLINE
H_CODEVERSION CODEVERSION NEWLINE
H_PRODUCER H_UNKNOWN NEWLINE
H_HOST IDENTIFIER NEWLINE
- H_COMPILESIZE IDENTIFIER {setCuobjdumparch($4);};
+ H_COMPILESIZE IDENTIFIER {setCuobjdumparch($4, cuobjdumpSectionList);};
| H_SEPARATOR NEWLINE
H_ARCH IDENTIFIER NEWLINE
H_CODEVERSION CODEVERSION NEWLINE
H_PRODUCER IDENTIFIER NEWLINE
H_HOST IDENTIFIER NEWLINE
- H_COMPILESIZE IDENTIFIER {setCuobjdumparch($4);};
+ H_COMPILESIZE IDENTIFIER {setCuobjdumparch($4, cuobjdumpSectionList);};
-identifier : H_IDENTIFIER FILENAME emptylines {setCuobjdumpidentifier($2);}
- | {setCuobjdumpidentifier("default");};
+identifier : H_IDENTIFIER FILENAME emptylines {setCuobjdumpidentifier($2, cuobjdumpSectionList);}
+ | {setCuobjdumpidentifier("default", cuobjdumpSectionList);};
compressedkeyword : H_COMPRESSED emptylines
| ;
-ptxcode : ptxcode PTXLINE {fprintf(ptxfile, "%s", $2);}
+ptxcode : ptxcode PTXLINE {fprintf(parser->ptxfile, "%s", $2);}
| ;
-elfcode : elfcode ELFLINE {fprintf(elffile, "%s", $2);}
+elfcode : elfcode ELFLINE {fprintf(parser->elffile, "%s", $2);}
| ;
-sasscode : sasscode SASSLINE {fprintf(sassfile, "%s", $2);}
+sasscode : sasscode SASSLINE {fprintf(parser->sassfile, "%s", $2);}
| ;
diff --git a/libcuda/gpgpu_context.h b/libcuda/gpgpu_context.h
new file mode 100644
index 0000000..45c5cdd
--- /dev/null
+++ b/libcuda/gpgpu_context.h
@@ -0,0 +1,71 @@
+#ifndef __gpgpu_context_h__
+#define __gpgpu_context_h__
+#include "cuda_api_object.h"
+#include "../src/cuda-sim/ptx_loader.h"
+#include "../src/cuda-sim/ptx_parser.h"
+#include "../src/gpgpusim_entrypoint.h"
+#include "../src/cuda-sim/cuda-sim.h"
+#include "../src/cuda-sim/cuda_device_runtime.h"
+#include "../src/cuda-sim/ptx-stats.h"
+
+class gpgpu_context {
+ public:
+ gpgpu_context() {
+ g_global_allfiles_symbol_table = NULL;
+ sm_next_access_uid=0;
+ warp_inst_sm_next_uid=0;
+ operand_info_sm_next_uid = 1;
+ kernel_info_m_next_uid = 1;
+ g_num_ptx_inst_uid = 0;
+ g_ptx_cta_info_uid = 1;
+ symbol_sm_next_uid = 1;
+ function_info_sm_next_uid = 1;
+ debug_tensorcore = 0;
+ api = new cuda_runtime_api(this);
+ ptxinfo = new ptxinfo_data(this);
+ ptx_parser = new ptx_recognizer(this);
+ the_gpgpusim = new GPGPUsim_ctx(this);
+ func_sim = new cuda_sim(this);
+ device_runtime = new cuda_device_runtime(this);
+ stats = new ptx_stats(this);
+ }
+ // global list
+ symbol_table *g_global_allfiles_symbol_table;
+ const char *g_filename;
+ unsigned sm_next_access_uid;
+ unsigned warp_inst_sm_next_uid;
+ unsigned operand_info_sm_next_uid;//uid for operand_info
+ unsigned kernel_info_m_next_uid;//uid for kernel_info_t
+ unsigned g_num_ptx_inst_uid; //uid for ptx inst inside ptx_instruction
+ unsigned long long g_ptx_cta_info_uid;
+ unsigned symbol_sm_next_uid; //uid for symbol
+ unsigned function_info_sm_next_uid;
+ std::vector<ptx_instruction*> s_g_pc_to_insn; // a direct mapping from PC to instruction
+ bool debug_tensorcore;
+
+ // objects pointers for each file
+ cuda_runtime_api* api;
+ ptxinfo_data* ptxinfo;
+ ptx_recognizer* ptx_parser;
+ GPGPUsim_ctx* the_gpgpusim;
+ cuda_sim* func_sim;
+ cuda_device_runtime* device_runtime;
+ ptx_stats* stats;
+ // member function list
+ void cuobjdumpParseBinary(unsigned int handle);
+ class symbol_table *gpgpu_ptx_sim_load_ptx_from_string( const char *p, unsigned source_num );
+ class symbol_table *gpgpu_ptx_sim_load_ptx_from_filename( const char *filename );
+ void gpgpu_ptx_info_load_from_filename( const char *filename, unsigned sm_version);
+ void gpgpu_ptxinfo_load_from_string( const char *p_for_info, unsigned source_num, unsigned sm_version=20, int no_of_ptx=0 );
+ void print_ptx_file( const char *p, unsigned source_num, const char *filename );
+ class symbol_table* init_parser(const char*);
+ class gpgpu_sim *gpgpu_ptx_sim_init_perf();
+ struct _cuda_device_id *GPGPUSim_Init();
+ void ptx_reg_options(option_parser_t opp);
+ const ptx_instruction* pc_to_instruction(unsigned pc);
+ const warp_inst_t *ptx_fetch_inst( address_type pc );
+ unsigned translate_pc_to_ptxlineno(unsigned pc);
+};
+gpgpu_context* GPGPU_Context();
+
+#endif /* __gpgpu_context_h__ */
diff --git a/libopencl/opencl_runtime_api.cc b/libopencl/opencl_runtime_api.cc
index 97a54d8..7f029c7 100644
--- a/libopencl/opencl_runtime_api.cc
+++ b/libopencl/opencl_runtime_api.cc
@@ -84,6 +84,7 @@
#include "../src/gpgpusim_entrypoint.h"
#include "../src/gpgpu-sim/gpu-sim.h"
#include "../src/gpgpu-sim/shader.h"
+#include "../libcuda/gpgpu_context.h"
//# define __my_func__ __PRETTY_FUNCTION__
# if defined __cplusplus ? __GNUC_PREREQ (2, 6) : __GNUC_PREREQ (2, 4)
@@ -424,6 +425,8 @@ void register_ptx_function( const char *name, function_info *impl )
void _cl_program::Build(const char *options)
{
+ gpgpu_context *ctx;
+ ctx = GPGPU_Context();
printf("GPGPU-Sim OpenCL API: compiling OpenCL kernels...\n");
std::map<cl_uint,pgm_info>::iterator i;
for( i = m_pgm.begin(); i!= m_pgm.end(); i++ ) {
@@ -534,7 +537,7 @@ void _cl_program::Build(const char *options)
exit(1);
}
}
- if( !g_keep_intermediate_files ) {
+ if( !ctx->ptxinfo->g_keep_intermediate_files ) {
// clean up files...
snprintf(commandline,1024,"rm -f %s", cl_fname );
int result = system(commandline);
@@ -576,8 +579,8 @@ void _cl_program::Build(const char *options)
}
}
info.m_asm = tmp;
- info.m_symtab = gpgpu_ptx_sim_load_ptx_from_string( tmp, source_num );
- gpgpu_ptxinfo_load_from_string( tmp, source_num );
+ info.m_symtab = ctx->gpgpu_ptx_sim_load_ptx_from_string( tmp, source_num );
+ ctx->gpgpu_ptxinfo_load_from_string( tmp, source_num );
free(tmp);
}
printf("GPGPU-Sim OpenCL API: finished compiling OpenCL kernels.\n");
@@ -645,7 +648,9 @@ class _cl_device_id *GPGPUSim_Init()
{
static _cl_device_id *the_device = NULL;
if( !the_device ) {
- gpgpu_sim *the_gpu = gpgpu_ptx_sim_init_perf();
+ gpgpu_context *ctx;
+ ctx = GPGPU_Context();
+ gpgpu_sim *the_gpu = ctx->gpgpu_ptx_sim_init_perf();
the_device = new _cl_device_id(the_gpu);
}
start_sim_thread(2);
@@ -872,14 +877,16 @@ clEnqueueNDRangeKernel(cl_command_queue command_queue,
const cl_event * event_wait_list,
cl_event * event) CL_API_SUFFIX__VERSION_1_0
{
+ gpgpu_context *ctx;
+ ctx = GPGPU_Context();
int _global_size[3];
int zeros[3] = { 0, 0, 0};
printf("\n\n\n");
char *mode = getenv("PTX_SIM_MODE_FUNC");
if ( mode )
- sscanf(mode,"%u", &g_ptx_sim_mode);
+ sscanf(mode,"%u", &(ctx->func_sim->g_ptx_sim_mode));
printf("GPGPU-Sim OpenCL API: clEnqueueNDRangeKernel '%s' (mode=%s)\n", kernel->name().c_str(),
- g_ptx_sim_mode?"functional simulation":"performance simulation");
+ (ctx->func_sim->g_ptx_sim_mode)?"functional simulation":"performance simulation");
if ( !work_dim || work_dim > 3 ) return CL_INVALID_WORK_DIMENSION;
size_t _local_size[3];
if( local_work_size != NULL ) {
@@ -943,15 +950,15 @@ clEnqueueNDRangeKernel(cl_command_queue command_queue,
gpgpu_t *gpu = command_queue->get_device()->the_device();
if (kernel->get_implementation()->get_ptx_version().ver() <3.0){
- gpgpu_ptx_sim_memcpy_symbol( "%_global_size", _global_size, 3 * sizeof(int), 0, 1, gpu );
- gpgpu_ptx_sim_memcpy_symbol( "%_work_dim", &work_dim, 1 * sizeof(int), 0, 1, gpu );
- gpgpu_ptx_sim_memcpy_symbol( "%_global_num_groups", &GridDim, 3 * sizeof(int), 0, 1, gpu );
- gpgpu_ptx_sim_memcpy_symbol( "%_global_launch_offset", zeros, 3 * sizeof(int), 0, 1, gpu );
- gpgpu_ptx_sim_memcpy_symbol( "%_global_block_offset", zeros, 3 * sizeof(int), 0, 1, gpu );
+ ctx->func_sim->gpgpu_ptx_sim_memcpy_symbol( "%_global_size", _global_size, 3 * sizeof(int), 0, 1, gpu );
+ ctx->func_sim->gpgpu_ptx_sim_memcpy_symbol( "%_work_dim", &work_dim, 1 * sizeof(int), 0, 1, gpu );
+ ctx->func_sim->gpgpu_ptx_sim_memcpy_symbol( "%_global_num_groups", &GridDim, 3 * sizeof(int), 0, 1, gpu );
+ ctx->func_sim->gpgpu_ptx_sim_memcpy_symbol( "%_global_launch_offset", zeros, 3 * sizeof(int), 0, 1, gpu );
+ ctx->func_sim->gpgpu_ptx_sim_memcpy_symbol( "%_global_block_offset", zeros, 3 * sizeof(int), 0, 1, gpu );
}
- kernel_info_t *grid = gpgpu_opencl_ptx_sim_init_grid(kernel->get_implementation(),params,GridDim,BlockDim,gpu);
- if ( g_ptx_sim_mode )
- gpgpu_opencl_ptx_sim_main_func( grid );
+ kernel_info_t *grid = ctx->func_sim->gpgpu_opencl_ptx_sim_init_grid(kernel->get_implementation(),params,GridDim,BlockDim,gpu);
+ if ( ctx->func_sim->g_ptx_sim_mode )
+ ctx->func_sim->gpgpu_opencl_ptx_sim_main_func( grid );
else
gpgpu_opencl_ptx_sim_main_perf( grid );
return CL_SUCCESS;
diff --git a/nightly.jenkinsfile b/nightly.jenkinsfile
index 5221b3b..e5ffa57 100644
--- a/nightly.jenkinsfile
+++ b/nightly.jenkinsfile
@@ -22,10 +22,12 @@ pipeline {
}
stage('nightly-simulations-build'){
steps{
+ sh 'if [ -d "./gpgpu-sim_simulations" ]; then \
+ cp -fr ./gpgpu-sim_simulations ./gpgpu-sim_simulations_bak; \
+ fi'
sh 'rm -rf gpgpu-sim_simulations'
- sh 'git clone [email protected]:TimRogersGroup/gpgpu-sim_simulations.git && \
+ sh 'git clone [email protected]:purdue-aalp/gpgpu-sim_simulations.git && \
cd gpgpu-sim_simulations && \
- git checkout purdue-cluster && \
git pull && \
ln -s /home/tgrogers-raid/a/common/data_dirs benchmarks/'
sh 'source /home/tgrogers-raid/a/common/gpgpu-sim-setup/9.1_env_setup.sh &&\
@@ -38,30 +40,64 @@ pipeline {
}
stage('nightly-2B-insn-run'){
steps {
+ sh 'rm -rf ./gpgpu-sim_simulations/util/plotting/correl-html && rm -rf gpgpu-sim-results-repo &&\
+ rm -rf ./gpgpu-sim_simulations/util/plotting/htmls'
+
sh 'source /home/tgrogers-raid/a/common/gpgpu-sim-setup/9.1_env_setup.sh &&\
- source `pwd`/setup_environment &&\
- ./gpgpu-sim_simulations/util/job_launching/run_simulations.py -B `cat ./gpgpu-sim_simulations/util/job_launching/apps/all-apps.list` -C TITANX-2B,TITANX-L1ON-2B,P100-2B,TITANV-2B -N nightly-$$ && \
- PLOTDIR="jenkins/${JOB_NAME}/${BUILD_NUMBER}/getstats" && ssh [email protected] mkdir -p /home/dynamo/a/tgrogers/website/gpgpu-sim-plots/$PLOTDIR && \
- ./gpgpu-sim_simulations/util/job_launching/monitor_func_test.py -I -S 1800 -v -s stats-$$.csv -N nightly-$$ && \
- ./gpgpu-sim_simulations/util/plotting/plot-get-stats.py -c stats-$$.csv -p [email protected]:~/website/gpgpu-sim-plots/$PLOTDIR -w https://engineering.purdue.edu/tgrogers/gpgpu-sim-plots/$PLOTDIR -n $PLOTDIR'
+ source `pwd`/setup_environment &&\
+ ./gpgpu-sim_simulations/util/job_launching/run_simulations.py \
+ -B `cat ./gpgpu-sim_simulations/util/job_launching/apps/all-apps.list` -C TITANV-2B -N nightly-$$ && \
+ ./gpgpu-sim_simulations/util/job_launching/monitor_func_test.py -I -S 1800 -v \
+ -s stats-per-app-9.1.csv -T 12 -K -N nightly-$$ && \
+ ./gpgpu-sim_simulations/util/plotting/plot-get-stats.py -c stats-per-app-9.1.csv -P cuda-9.1.nightly'
}
}
stage('nightly-correlate'){
steps {
+ sh 'git clone [email protected]:purdue-aalp/gpgpu-sim-results-repo.git'
+
+ sh 'if [ ! -d ./gpgpu-sim-results-repo/${JOB_NAME} ]; then \
+ mkdir -p ./gpgpu-sim-results-repo/${JOB_NAME}/ ; \
+ cp ./gpgpu-sim-results-repo/purdue-aalp/gpgpu-sim_distribution/dev/* \
+ ./gpgpu-sim-results-repo/${JOB_NAME}/ ; \
+ fi && \
+ ./gpgpu-sim_simulations/run_hw/get_hw_data.sh'
+
sh 'source /home/tgrogers-raid/a/common/gpgpu-sim-setup/9.1_env_setup.sh &&\
+ ./gpgpu-sim_simulations/util/job_launching/get_stats.py -R -K -k \
+ -B `cat ./gpgpu-sim_simulations/util/job_launching/apps/all-apps.list` \
+ -C TITANV-2B > stats-per-kernel-9.1.csv &&\
+ ./gpgpu-sim_simulations/util/plotting/merge-stats.py \
+ -c ./gpgpu-sim-results-repo/${JOB_NAME}/stats-per-app-9.1.csv,./stats-per-app-9.1.csv -R \
+ > per-app-merge-9.1.csv &&\
+ ./gpgpu-sim_simulations/util/plotting/merge-stats.py \
+ -c ./gpgpu-sim-results-repo/${JOB_NAME}/stats-per-kernel-9.1.csv,./stats-per-kernel-9.1.csv -R \
+ > per-kernel-merge-9.1.csv &&\
source `pwd`/setup_environment &&\
- PLOTDIR="jenkins/${JOB_NAME}" &&\
- ./gpgpu-sim_simulations/util/job_launching/get_stats.py -R -K -k -B `cat ./gpgpu-sim_simulations/util/job_launching/apps/all-apps.list` -C TITANX-2B,TITANX-L1ON-2B,P100-2B,TITANV-2B > nightly-stats-per-kernel-9.1.csv &&\
- ./gpgpu-sim_simulations/util/plotting/correlate_and_publish.sh nightly-stats-per-kernel-9.1.csv $PLOTDIR ${BUILD_NUMBER}'
+ ./gpgpu-sim_simulations/util/plotting/plot-correlation.py -c per-kernel-merge-9.1.csv \
+ -p cuda-9.1.nightly -b ./gpgpu-sim_simulations/util/plotting/known.correlation.outliers.list \
+ | grep "Correl=" | tee correl.9.1.txt &&\
+ cp stats-per-*.csv ./gpgpu-sim-results-repo/${JOB_NAME}/ &&\
+ cd ./gpgpu-sim-results-repo &&\
+ git pull &&\
+ git diff --quiet && git diff --staged --quiet || git commit -am "Jenkins automated checkin ${JOB_NAME} Build:${BUILD_NUMBER}" &&\
+ git push'
+
+ sh 'PLOTDIR="/home/dynamo/a/tgrogers/website/gpgpu-sim-plots/jenkins/${JOB_NAME}" &&\
+ ssh [email protected] mkdir -p $PLOTDIR/${BUILD_NUMBER} && \
+ scp ./gpgpu-sim_simulations/util/plotting/correl-html/* [email protected]:$PLOTDIR/${BUILD_NUMBER} &&\
+ scp ./gpgpu-sim_simulations/util/plotting/htmls/* [email protected]:$PLOTDIR/${BUILD_NUMBER} &&\
+ ssh [email protected] "cd $PLOTDIR && rm -rf latest && cp -r ${BUILD_NUMBER} latest"'
}
}
}
post {
success {
- emailext body: "See ${BUILD_URL}",
+ emailext body:'''${SCRIPT, template="groovy-html.nightly.success.template"}''',
recipientProviders: [[$class: 'CulpritsRecipientProvider'],
[$class: 'RequesterRecipientProvider']],
subject: "[AALP Jenkins] Build #${BUILD_NUMBER} - Success!",
+ attachmentsPattern: 'correl.*.txt',
}
failure {
diff --git a/setup_environment b/setup_environment
index 17891ce..58f4713 100644
--- a/setup_environment
+++ b/setup_environment
@@ -148,19 +148,15 @@ fi
echo "";
echo "----------------------------------------------------------------------------";
echo "INFO - If you only care about PTX execution, ignore this message. GPGPU-Sim supports PTX execution in modern CUDA."
-if [ $CUDA_VERSION_NUMBER -gt 4200 ]; then
- echo "If you want to run PTXPLUS (sm_1x SASS) with a modern card configuration, the apps and simulator must be compiled with CUDA 4.2."
- echo "You can still run a PASCAL configuration when compiling with 4.2 by setting the \$PTXAS_CUDA_INSTALL_PATH directory environment variable."
-else
- echo "If you want to run PTXPLUS (sm_1x SASS) with a modern card configuration - set the envronment variable"
- echo "\$PTXAS_CUDA_INSTALL_PATH to point a CUDA version compabible with your card configurations (i.e. 8+ for PASCAL, 9+ for VOLTA etc..)"
- echo "For example: \"export \$PTXAS_CUDA_INSTALL_PATH=/usr/local/cuda-9.1\""
-fi
+echo "If you want to run PTXPLUS (sm_1x SASS) with a modern card configuration - set the envronment variable"
+echo "\$PTXAS_CUDA_INSTALL_PATH to point a CUDA version compabible with your card configurations (i.e. 8+ for PASCAL, 9+ for VOLTA etc..)"
+echo "For example: \"export \$PTXAS_CUDA_INSTALL_PATH=/usr/local/cuda-9.1\""
+echo ""
echo "The following text describes why:";
echo "If you are using PTXPLUS, only sm_1x is supported and it requires that the app and simulator binaries are compiled in CUDA 4.2 or less.";
echo "The simulator requires it since CUDA headers desribe struct sizes in the exec which change from gen to gen.";
echo "The apps require 4.2 because new versions of CUDA tools have dropped parsing support for generating sm_1x";
-echo "When running using modern config (i.e. pascal) and PTXPLUS with CUDA 4.2, the \$PTXAS_CUDA_INSTALL_PATH env variable is required to get proper register usage"
+echo "When running using modern config (i.e. volta) and PTXPLUS with CUDA 4.2, the \$PTXAS_CUDA_INSTALL_PATH env variable is required to get proper register usage"
echo "(and hence occupancy) using a version of CUDA that knows the register usage on the real card."
echo "";
echo "----------------------------------------------------------------------------";
diff --git a/src/Makefile b/src/Makefile
index 6001669..3ad511e 100644
--- a/src/Makefile
+++ b/src/Makefile
@@ -51,6 +51,8 @@ else
CXXFLAGS +=
endif
+CXXFLAGS += -I$(CUDA_INSTALL_PATH)/include
+
OPTFLAGS += -g3 -fPIC
CPP = g++ $(SNOW)
diff --git a/src/abstract_hardware_model.cc b/src/abstract_hardware_model.cc
index 023f51b..9a91818 100644
--- a/src/abstract_hardware_model.cc
+++ b/src/abstract_hardware_model.cc
@@ -34,13 +34,33 @@
#include "cuda-sim/cuda-sim.h"
#include "gpgpu-sim/gpu-sim.h"
#include "option_parser.h"
+#include "gpgpusim_entrypoint.h"
#include <algorithm>
#include <sys/stat.h>
#include <sstream>
#include <iostream>
+#include "../libcuda/gpgpu_context.h"
-unsigned mem_access_t::sm_next_access_uid = 0;
-unsigned warp_inst_t::sm_next_uid = 0;
+void mem_access_t::init(gpgpu_context* ctx)
+{
+ gpgpu_ctx = ctx;
+ m_uid=++(gpgpu_ctx->sm_next_access_uid);
+ m_addr=0;
+ m_req_size=0;
+}
+void warp_inst_t::issue( const active_mask_t &mask, unsigned warp_id, unsigned long long cycle, int dynamic_warp_id, int sch_id )
+{
+ m_warp_active_mask = mask;
+ m_warp_issued_mask = mask;
+ m_uid = ++(m_config->gpgpu_ctx->warp_inst_sm_next_uid);
+ m_warp_id = warp_id;
+ m_dynamic_warp_id = dynamic_warp_id;
+ issue_cycle = cycle;
+ cycles = initiation_interval;
+ m_cache_hit=false;
+ m_empty=false;
+ m_scheduler_id=sch_id;
+}
checkpoint::checkpoint()
{
@@ -172,9 +192,10 @@ void gpgpu_functional_sim_config::ptx_set_tex_cache_linesize(unsigned linesize)
m_texcache_linesize = linesize;
}
-gpgpu_t::gpgpu_t( const gpgpu_functional_sim_config &config )
+gpgpu_t::gpgpu_t( const gpgpu_functional_sim_config &config, gpgpu_context* ctx )
: m_function_model_config(config)
{
+ gpgpu_ctx = ctx;
m_global_mem = new memory_space_impl<8192>("global",64*1024);
m_tex_mem = new memory_space_impl<8192>("tex",64*1024);
@@ -198,6 +219,9 @@ gpgpu_t::gpgpu_t( const gpgpu_functional_sim_config &config )
if(m_function_model_config.get_ptx_inst_debug_to_file() != 0)
ptx_inst_debug_file = fopen(m_function_model_config.get_ptx_inst_debug_file(), "w");
+
+ gpu_sim_cycle=0;
+ gpu_tot_sim_cycle=0;
}
address_type line_size_based_tag_func(new_addr_type address, new_addr_type line_size)
@@ -402,7 +426,7 @@ void warp_inst_t::generate_mem_accesses()
}
assert( total_accesses > 0 && total_accesses <= m_config->warp_size );
cycles = total_accesses; // shared memory conflicts modeled as larger initiation interval
- ptx_file_line_stats_add_smem_bank_conflict( pc, total_accesses );
+ m_config->gpgpu_ctx->stats->ptx_file_line_stats_add_smem_bank_conflict( pc, total_accesses );
break;
}
@@ -443,11 +467,11 @@ void warp_inst_t::generate_mem_accesses()
byte_mask.set(idx+i);
}
for( a=accesses.begin(); a != accesses.end(); ++a )
- m_accessq.push_back( mem_access_t(access_type,a->first,cache_block_size,is_write,a->second, byte_mask, mem_access_sector_mask_t()));
+ m_accessq.push_back( mem_access_t(access_type,a->first,cache_block_size,is_write,a->second, byte_mask, mem_access_sector_mask_t(), m_config->gpgpu_ctx));
}
if ( space.get_type() == global_space ) {
- ptx_file_line_stats_add_uncoalesced_gmem( pc, m_accessq.size() - starting_queue_size );
+ m_config->gpgpu_ctx->stats->ptx_file_line_stats_add_uncoalesced_gmem( pc, m_accessq.size() - starting_queue_size );
}
m_mem_accesses_created=true;
}
@@ -675,21 +699,16 @@ void warp_inst_t::memory_coalescing_arch_reduce_and_send( bool is_write, mem_acc
assert(lower_half_used && upper_half_used);
}
}
- m_accessq.push_back( mem_access_t(access_type,addr,size,is_write,info.active,info.bytes, info.chunks) );
+ m_accessq.push_back( mem_access_t(access_type,addr,size,is_write,info.active,info.bytes, info.chunks,m_config->gpgpu_ctx) );
}
void warp_inst_t::completed( unsigned long long cycle ) const
{
unsigned long long latency = cycle - issue_cycle;
assert(latency <= cycle); // underflow detection
- ptx_file_line_stats_add_latency(pc, latency * active_count());
+ m_config->gpgpu_ctx->stats->ptx_file_line_stats_add_latency(pc, latency * active_count());
}
-//Jin: CDP support
-bool g_cdp_enabled;
-unsigned g_kernel_launch_latency;
-
-unsigned kernel_info_t::m_next_uid = 1;
kernel_info_t::kernel_info_t( dim3 gridDim, dim3 blockDim, class function_info *entry)
{
@@ -701,14 +720,14 @@ kernel_info_t::kernel_info_t( dim3 gridDim, dim3 blockDim, class function_info *
m_next_cta.z=0;
m_next_tid=m_next_cta;
m_num_cores_running=0;
- m_uid = m_next_uid++;
+ m_uid = (entry->gpgpu_ctx->kernel_info_m_next_uid)++;
m_param_mem = new memory_space_impl<8192>("param",64*1024);
//Jin: parent and child kernel management for CDP
m_parent_kernel = NULL;
//Jin: launch latency management
- m_launch_latency = g_kernel_launch_latency;
+ m_launch_latency = entry->gpgpu_ctx->device_runtime->g_kernel_launch_latency;
volta_cache_config_set=false;
}
@@ -726,14 +745,14 @@ kernel_info_t::kernel_info_t( dim3 gridDim, dim3 blockDim, class function_info *
m_next_cta.z=0;
m_next_tid=m_next_cta;
m_num_cores_running=0;
- m_uid = m_next_uid++;
+ m_uid = (entry->gpgpu_ctx->kernel_info_m_next_uid)++;
m_param_mem = new memory_space_impl<8192>("param",64*1024);
//Jin: parent and child kernel management for CDP
m_parent_kernel = NULL;
//Jin: launch latency management
- m_launch_latency = g_kernel_launch_latency;
+ m_launch_latency = entry->gpgpu_ctx->device_runtime->g_kernel_launch_latency;
volta_cache_config_set=false;
m_NameToCudaArray = nameToCudaArray;
@@ -787,17 +806,16 @@ bool kernel_info_t::children_all_finished() {
void kernel_info_t::notify_parent_finished() {
if(m_parent_kernel) {
- extern unsigned long long g_total_param_size;
- g_total_param_size -= ((m_kernel_entry->get_args_aligned_size() + 255)/256*256);
+ m_kernel_entry->gpgpu_ctx->device_runtime->g_total_param_size -= ((m_kernel_entry->get_args_aligned_size() + 255)/256*256);
m_parent_kernel->remove_child(this);
- g_stream_manager->register_finished_kernel(m_parent_kernel->get_uid());
+ g_stream_manager()->register_finished_kernel(m_parent_kernel->get_uid());
}
}
CUstream_st * kernel_info_t::create_stream_cta(dim3 ctaid) {
assert(get_default_stream_cta(ctaid));
CUstream_st * stream = new CUstream_st();
- g_stream_manager->add_stream(stream);
+ g_stream_manager()->add_stream(stream);
assert(m_cta_streams.find(ctaid) != m_cta_streams.end());
assert(m_cta_streams[ctaid].size() >= 1); //must have default stream
m_cta_streams[ctaid].push_back(stream);
@@ -813,7 +831,7 @@ CUstream_st * kernel_info_t::get_default_stream_cta(dim3 ctaid) {
else {
m_cta_streams[ctaid] = std::list<CUstream_st *>();
CUstream_st * stream = new CUstream_st();
- g_stream_manager->add_stream(stream);
+ g_stream_manager()->add_stream(stream);
m_cta_streams[ctaid].push_back(stream);
return stream;
}
@@ -845,17 +863,18 @@ void kernel_info_t::destroy_cta_streams() {
for(auto s = m_cta_streams.begin(); s != m_cta_streams.end(); s++) {
stream_size += s->second.size();
for(auto ss = s->second.begin(); ss != s->second.end(); ss++)
- g_stream_manager->destroy_stream(*ss);
+ g_stream_manager()->destroy_stream(*ss);
s->second.clear();
}
printf("size %lu\n", stream_size);
m_cta_streams.clear();
}
-simt_stack::simt_stack( unsigned wid, unsigned warpSize)
+simt_stack::simt_stack( unsigned wid, unsigned warpSize, class gpgpu_sim * gpu)
{
m_warp_id=wid;
m_warp_size = warpSize;
+ m_gpu=gpu;
reset();
}
@@ -961,7 +980,7 @@ void simt_stack::print (FILE *fout) const
} else {
fprintf(fout," " );
}
- ptx_print_insn( stack_entry.m_pc, fout );
+ m_gpu->gpgpu_ctx->func_sim->ptx_print_insn( stack_entry.m_pc, fout );
fprintf(fout,"\n");
}
@@ -1055,7 +1074,7 @@ void simt_stack::update( simt_mask_t &thread_done, addr_vector_t &next_pc, addre
simt_stack_entry new_stack_entry;
new_stack_entry.m_pc = tmp_next_pc;
new_stack_entry.m_active_mask = tmp_active_mask;
- new_stack_entry.m_branch_div_cycle = gpu_sim_cycle+gpu_tot_sim_cycle;
+ new_stack_entry.m_branch_div_cycle = m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle;
new_stack_entry.m_type = STACK_ENTRY_TYPE_CALL;
m_stack.push_back(new_stack_entry);
return;
@@ -1087,7 +1106,7 @@ void simt_stack::update( simt_mask_t &thread_done, addr_vector_t &next_pc, addre
new_recvg_pc = recvg_pc;
if (new_recvg_pc != top_recvg_pc) {
m_stack.back().m_pc = new_recvg_pc;
- m_stack.back().m_branch_div_cycle = gpu_sim_cycle+gpu_tot_sim_cycle;
+ m_stack.back().m_branch_div_cycle = m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle;
m_stack.push_back(simt_stack_entry());
}
@@ -1113,7 +1132,7 @@ void simt_stack::update( simt_mask_t &thread_done, addr_vector_t &next_pc, addre
if (warp_diverged) {
- ptx_file_line_stats_add_warp_divergence(top_pc, 1);
+ m_gpu->gpgpu_ctx->stats->ptx_file_line_stats_add_warp_divergence(top_pc, 1);
}
}
@@ -1160,7 +1179,7 @@ warp_inst_t core_t::getExecuteWarp(unsigned warpId)
{
unsigned pc,rpc;
m_simt_stack[warpId]->get_pdom_stack_top_info(&pc,&rpc);
- warp_inst_t wi= *ptx_fetch_inst(pc);
+ warp_inst_t wi= *(m_gpu->gpgpu_ctx->ptx_fetch_inst(pc));
wi.set_active(m_simt_stack[warpId]->get_active_mask());
return wi;
}
@@ -1179,7 +1198,7 @@ void core_t::initilizeSIMTStack(unsigned warp_count, unsigned warp_size)
{
m_simt_stack = new simt_stack*[warp_count];
for (unsigned i = 0; i < warp_count; ++i)
- m_simt_stack[i] = new simt_stack(i,warp_size);
+ m_simt_stack[i] = new simt_stack(i,warp_size,m_gpu);
m_warp_size = warp_size;
m_warp_count = warp_count;
}
diff --git a/src/abstract_hardware_model.h b/src/abstract_hardware_model.h
index 27a1ba6..8c19e33 100644
--- a/src/abstract_hardware_model.h
+++ b/src/abstract_hardware_model.h
@@ -31,6 +31,8 @@
// Forward declarations
class gpgpu_sim;
class kernel_info_t;
+class gpgpu_context;
+
//Set a hard limit of 32 CTAs per shader [cuda only has 8]
#define MAX_CTA_PER_SHADER 32
@@ -173,9 +175,7 @@ enum _memory_op_t {
#include <algorithm>
#if !defined(__VECTOR_TYPES_H__)
-struct dim3 {
- unsigned int x, y, z;
-};
+#include "vector_types.h"
#endif
struct dim3comp {
bool operator() (const dim3 & a, const dim3 & b) const
@@ -197,7 +197,7 @@ void increment_x_then_y_then_z( dim3 &i, const dim3 &bound);
#include "stream_manager.h"
class stream_manager;
struct CUstream_st;
-extern stream_manager * g_stream_manager;
+//extern stream_manager * g_stream_manager;
//support for pinned memories added
extern std::map<void *,void **> pinned_memory;
extern std::map<void *, size_t> pinned_memory_size;
@@ -300,7 +300,6 @@ private:
class function_info *m_kernel_entry;
unsigned m_uid;
- static unsigned m_next_uid;
//These maps contain the snapshot of the texture mappings at kernel launch
std::map<std::string, const struct cudaArray*> m_NameToCudaArray;
@@ -348,9 +347,11 @@ public:
mutable bool volta_cache_config_set;
};
-struct core_config {
- core_config()
- {
+class core_config {
+ public:
+ core_config(gpgpu_context* ctx)
+ {
+ gpgpu_ctx = ctx;
m_valid = false;
num_shmem_bank=16;
shmem_limited_broadcast = false;
@@ -362,6 +363,8 @@ struct core_config {
bool m_valid;
unsigned warp_size;
+ // backward pointer
+ class gpgpu_context* gpgpu_ctx;
// off-chip memory request architecture parameters
int gpgpu_coalesce_arch;
@@ -400,7 +403,7 @@ typedef std::vector<address_type> addr_vector_t;
class simt_stack {
public:
- simt_stack( unsigned wid, unsigned warpSize);
+ simt_stack( unsigned wid, unsigned warpSize, class gpgpu_sim * gpu);
void reset();
void launch( address_type start_pc, const simt_mask_t &active_mask );
@@ -417,6 +420,7 @@ protected:
unsigned m_warp_id;
unsigned m_warp_size;
+
enum stack_entry_type {
STACK_ENTRY_TYPE_NORMAL = 0,
STACK_ENTRY_TYPE_CALL
@@ -434,6 +438,8 @@ protected:
};
std::deque<simt_stack_entry> m_stack;
+
+ class gpgpu_sim * m_gpu;
};
#define GLOBAL_HEAP_START 0xC0000000
@@ -452,19 +458,7 @@ protected:
#if !defined(__CUDA_RUNTIME_API_H__)
-enum cudaChannelFormatKind {
- cudaChannelFormatKindSigned,
- cudaChannelFormatKindUnsigned,
- cudaChannelFormatKindFloat
-};
-
-struct cudaChannelFormatDesc {
- int x;
- int y;
- int z;
- int w;
- enum cudaChannelFormatKind f;
-};
+#include "builtin_types.h"
struct cudaArray {
void *devPtr;
@@ -476,28 +470,6 @@ struct cudaArray {
unsigned dimensions;
};
-enum cudaTextureAddressMode {
- cudaAddressModeWrap,
- cudaAddressModeClamp
-};
-
-enum cudaTextureFilterMode {
- cudaFilterModePoint,
- cudaFilterModeLinear
-};
-
-enum cudaTextureReadMode {
- cudaReadModeElementType,
- cudaReadModeNormalizedFloat
-};
-
-struct textureReference {
- int normalized;
- enum cudaTextureFilterMode filterMode;
- enum cudaTextureAddressMode addressMode[3];
- struct cudaChannelFormatDesc channelDesc;
-};
-
#endif
// Struct that record other attributes in the textureReference declaration
@@ -563,7 +535,9 @@ private:
class gpgpu_t {
public:
- gpgpu_t( const gpgpu_functional_sim_config &config );
+ gpgpu_t( const gpgpu_functional_sim_config &config, gpgpu_context* ctx );
+ // backward pointer
+ class gpgpu_context* gpgpu_ctx;
int checkpoint_option;
int checkpoint_kernel;
int checkpoint_CTA;
@@ -572,6 +546,12 @@ public:
int resume_CTA;
int checkpoint_CTA_t;
int checkpoint_insn_Y;
+
+ //Move some cycle core stats here instead of being global
+ unsigned long long gpu_sim_cycle;
+ unsigned long long gpu_tot_sim_cycle;
+
+
void* gpu_malloc( size_t size );
void* gpu_mallocarray( size_t count );
void gpu_memset( size_t dst_start_addr, int c, size_t count );
@@ -752,13 +732,14 @@ enum cache_operator_type {
class mem_access_t {
public:
- mem_access_t() { init(); }
+ mem_access_t(gpgpu_context* ctx) { init(ctx); }
mem_access_t( mem_access_type type,
new_addr_type address,
unsigned size,
- bool wr )
+ bool wr,
+ gpgpu_context* ctx)
{
- init();
+ init(ctx);
m_type = type;
m_addr = address;
m_req_size = size;
@@ -770,10 +751,11 @@ public:
bool wr,
const active_mask_t &active_mask,
const mem_access_byte_mask_t &byte_mask,
- const mem_access_sector_mask_t &sector_mask)
+ const mem_access_sector_mask_t &sector_mask,
+ gpgpu_context* ctx)
: m_warp_mask(active_mask), m_byte_mask(byte_mask), m_sector_mask(sector_mask)
{
- init();
+ init(ctx);
m_type = type;
m_addr = address;
m_req_size = size;
@@ -806,13 +788,9 @@ public:
}
}
+ gpgpu_context* gpgpu_ctx;
private:
- void init()
- {
- m_uid=++sm_next_access_uid;
- m_addr=0;
- m_req_size=0;
- }
+ void init(gpgpu_context* ctx);
unsigned m_uid;
new_addr_type m_addr; // request address
@@ -822,8 +800,6 @@ private:
active_mask_t m_warp_mask;
mem_access_byte_mask_t m_byte_mask;
mem_access_sector_mask_t m_sector_mask;
-
- static unsigned sm_next_access_uid;
};
class mem_fetch;
@@ -836,8 +812,8 @@ public:
class mem_fetch_allocator {
public:
- virtual mem_fetch *alloc( new_addr_type addr, mem_access_type type, unsigned size, bool wr ) const = 0;
- virtual mem_fetch *alloc( const class warp_inst_t &inst, const mem_access_t &access ) const = 0;
+ virtual mem_fetch *alloc( new_addr_type addr, mem_access_type type, unsigned size, bool wr, unsigned long long cycle ) const = 0;
+ virtual mem_fetch *alloc( const class warp_inst_t &inst, const mem_access_t &access, unsigned long long cycle ) const = 0;
};
// the maximum number of destination, source, or address uarch operands in a instruction
@@ -958,7 +934,7 @@ public:
m_empty=true;
m_config=NULL;
}
- warp_inst_t( const core_config *config )
+ warp_inst_t( const core_config *config )
{
m_uid=0;
assert(config->warp_size<=MAX_WARP_SIZE);
@@ -982,19 +958,9 @@ public:
{
m_empty=true;
}
- void issue( const active_mask_t &mask, unsigned warp_id, unsigned long long cycle, int dynamic_warp_id, int sch_id )
- {
- m_warp_active_mask = mask;
- m_warp_issued_mask = mask;
- m_uid = ++sm_next_uid;
- m_warp_id = warp_id;
- m_dynamic_warp_id = dynamic_warp_id;
- issue_cycle = cycle;
- cycles = initiation_interval;
- m_cache_hit=false;
- m_empty=false;
- m_scheduler_id=sch_id;
- }
+
+ void issue( const active_mask_t &mask, unsigned warp_id, unsigned long long cycle, int dynamic_warp_id, int sch_id );
+
const active_mask_t & get_active_mask() const
{
return m_warp_active_mask;
@@ -1129,7 +1095,6 @@ public:
unsigned get_uid() const { return m_uid; }
unsigned get_schd_id() const { return m_scheduler_id; }
-
protected:
unsigned m_uid;
@@ -1158,8 +1123,6 @@ protected:
bool m_mem_accesses_created;
std::list<mem_access_t> m_accessq;
- static unsigned sm_next_uid;
-
unsigned m_scheduler_id; //the scheduler that issues this inst
//Jin: cdp support
diff --git a/src/cuda-sim/Makefile b/src/cuda-sim/Makefile
index 999dad7..85d1c8c 100644
--- a/src/cuda-sim/Makefile
+++ b/src/cuda-sim/Makefile
@@ -79,16 +79,16 @@ libgpgpu_ptx_sim.a: $(OBJS)
ar rcs $(OUTPUT_DIR)/libgpgpu_ptx_sim.a $(OUTPUT_DIR)/ptx.tab.o $(OUTPUT_DIR)/lex.ptx_.o $(OUTPUT_DIR)/ptxinfo.tab.o $(OUTPUT_DIR)/lex.ptxinfo_.o $(OBJS)
$(OUTPUT_DIR)/ptx.tab.o: $(OUTPUT_DIR)/ptx.tab.c
- $(CPP) -c $(OPT) -DYYDEBUG $(OUTPUT_DIR)/ptx.tab.c -o $(OUTPUT_DIR)/ptx.tab.o
+ $(CPP) -c $(CXX_OPT) -DYYDEBUG $(OUTPUT_DIR)/ptx.tab.c -o $(OUTPUT_DIR)/ptx.tab.o
$(OUTPUT_DIR)/lex.ptx_.o: $(OUTPUT_DIR)/lex.ptx_.c
- $(CPP) -c $(OPT) $(OUTPUT_DIR)/lex.ptx_.c -o $(OUTPUT_DIR)/lex.ptx_.o
+ $(CPP) -c $(CXX_OPT) $(OUTPUT_DIR)/lex.ptx_.c -o $(OUTPUT_DIR)/lex.ptx_.o
$(OUTPUT_DIR)/ptxinfo.tab.o: $(OUTPUT_DIR)/ptxinfo.tab.c
- $(CPP) -c $(OPT) -DYYDEBUG $(OUTPUT_DIR)/ptxinfo.tab.c -o $(OUTPUT_DIR)/ptxinfo.tab.o
+ $(CPP) -c $(CXX_OPT) -DYYDEBUG $(OUTPUT_DIR)/ptxinfo.tab.c -o $(OUTPUT_DIR)/ptxinfo.tab.o
$(OUTPUT_DIR)/lex.ptxinfo_.o: $(OUTPUT_DIR)/lex.ptxinfo_.c $(OUTPUT_DIR)/ptxinfo.tab.c
- $(CPP) -c $(OPT) $(OUTPUT_DIR)/lex.ptxinfo_.c -o $(OUTPUT_DIR)/lex.ptxinfo_.o
+ $(CPP) -c $(CXX_OPT) $(OUTPUT_DIR)/lex.ptxinfo_.c -o $(OUTPUT_DIR)/lex.ptxinfo_.o
$(OUTPUT_DIR)/ptx.tab.c: ptx.y
bison --name-prefix=ptx_ -v -d ptx.y --file-prefix=$(OUTPUT_DIR)/ptx
diff --git a/src/cuda-sim/cuda-math.h b/src/cuda-sim/cuda-math.h
index a5db337..9a5468c 100644
--- a/src/cuda-sim/cuda-math.h
+++ b/src/cuda-sim/cuda-math.h
@@ -277,10 +277,10 @@ int float2int(float a, enum cudaRoundMode mode)
{
int tmp;
switch (mode) {
- case cuda_math::cudaRoundZero: tmp = truncf(a); break;
- case cuda_math::cudaRoundNearest: tmp = nearbyintf(a); break;
- case cuda_math::cudaRoundMinInf: tmp = floorf(a); break;
- case cuda_math::cudaRoundPosInf: tmp = ceilf(a); break;
+ case cudaRoundZero: tmp = truncf(a); break;
+ case cudaRoundNearest: tmp = nearbyintf(a); break;
+ case cudaRoundMinInf: tmp = floorf(a); break;
+ case cudaRoundPosInf: tmp = ceilf(a); break;
default: abort();
}
return tmp;
@@ -296,10 +296,10 @@ unsigned int float2uint(float a, enum cudaRoundMode mode)
{
unsigned int tmp;
switch (mode) {
- case cuda_math::cudaRoundZero: tmp = truncf(a); break;
- case cuda_math::cudaRoundNearest: tmp = nearbyintf(a); break;
- case cuda_math::cudaRoundMinInf: tmp = floorf(a); break;
- case cuda_math::cudaRoundPosInf: tmp = ceilf(a); break;
+ case cudaRoundZero: tmp = truncf(a); break;
+ case cudaRoundNearest: tmp = nearbyintf(a); break;
+ case cudaRoundMinInf: tmp = floorf(a); break;
+ case cudaRoundPosInf: tmp = ceilf(a); break;
default: abort();
}
return tmp;
diff --git a/src/cuda-sim/cuda-sim.cc b/src/cuda-sim/cuda-sim.cc
index 4c0fc58..1b0e841 100644
--- a/src/cuda-sim/cuda-sim.cc
+++ b/src/cuda-sim/cuda-sim.cc
@@ -30,6 +30,8 @@
#include "instructions.h"
#include "ptx_ir.h"
+class ptx_recognizer;
+typedef void * yyscan_t;
#include "ptx.tab.h"
#include "ptx_sim.h"
#include <stdio.h>
@@ -49,27 +51,13 @@
#include "decuda_pred_table/decuda_pred_table.h"
#include "../stream_manager.h"
#include "cuda_device_runtime.h"
+#include "../../libcuda/gpgpu_context.h"
-int gpgpu_ptx_instruction_classification;
-void ** g_inst_classification_stat = NULL;
-void ** g_inst_op_classification_stat= NULL;
-int g_ptx_kernel_count = -1; // used for classification stat collection purposes
int g_debug_execution = 0;
-int g_debug_thread_uid = 0;
-addr_t g_debug_pc = 0xBEEF1518;
// Output debug information to file options
-int cp_count;
-int cp_cta_resume;
-unsigned g_ptx_sim_num_insn = 0;
-unsigned gpgpu_param_num_shaders = 0;
-char *opcode_latency_int, *opcode_latency_fp, *opcode_latency_dp,*opcode_latency_sfu,*opcode_latency_tensor;
-char *opcode_initiation_int, *opcode_initiation_fp, *opcode_initiation_dp,*opcode_initiation_sfu,*opcode_initiation_tensor;
-char *cdp_latency_str;
-unsigned cdp_latency[5];
-
-void ptx_opcocde_latency_options (option_parser_t opp) {
+void cuda_sim::ptx_opcocde_latency_options (option_parser_t opp) {
option_parser_register(opp, "-ptx_opcode_latency_int", OPT_CSTR, &opcode_latency_int,
"Opcode latencies for integers <ADD,MAX,MUL,MAD,DIV>"
"Default 1,1,19,25,145",
@@ -118,8 +106,6 @@ cudaLaunchDeviceV2_init_perWarp, cudaLaunchDevicV2_perKernel>"
"7200,8000,100,12000,1600");
}
-static address_type get_converge_point(address_type pc);
-
void gpgpu_t::gpgpu_ptx_sim_bindNameToTexture(const char* name, const struct textureReference* texref, int dim, int readmode, int ext)
{
std::string texname(name);
@@ -229,10 +215,6 @@ void gpgpu_t::gpgpu_ptx_sim_unbindTexture(const struct textureReference* texref)
m_NameToTextureInfo.erase(texname);
}
-unsigned g_assemble_code_next_pc=0;
-std::map<unsigned,function_info*> g_pc_to_finfo;
-std::vector<ptx_instruction*> function_info::s_g_pc_to_insn;
-
#define MAX_INST_SIZE 8 /*bytes*/
void function_info::ptx_assemble()
@@ -250,39 +232,39 @@ void function_info::ptx_assemble()
fflush(stdout);
std::list<ptx_instruction*>::iterator i;
- addr_t PC = g_assemble_code_next_pc; // globally unique address (across functions)
+ addr_t PC = gpgpu_ctx->func_sim->g_assemble_code_next_pc; // globally unique address (across functions)
// start function on an aligned address
for( unsigned i=0; i < (PC%MAX_INST_SIZE); i++ )
- s_g_pc_to_insn.push_back((ptx_instruction*)NULL);
+ gpgpu_ctx->s_g_pc_to_insn.push_back((ptx_instruction*)NULL);
PC += PC%MAX_INST_SIZE;
m_start_PC = PC;
addr_t n=0; // offset in m_instr_mem
//Why s_g_pc_to_insn.size() is needed to reserve additional memory for insts? reserve is cumulative.
//s_g_pc_to_insn.reserve(s_g_pc_to_insn.size() + MAX_INST_SIZE*m_instructions.size());
- s_g_pc_to_insn.reserve(MAX_INST_SIZE*m_instructions.size());
+ gpgpu_ctx->s_g_pc_to_insn.reserve(MAX_INST_SIZE*m_instructions.size());
for ( i=m_instructions.begin(); i != m_instructions.end(); i++ ) {
ptx_instruction *pI = *i;
if ( pI->is_label() ) {
const symbol *l = pI->get_label();
labels[l->name()] = n;
} else {
- g_pc_to_finfo[PC] = this;
+ gpgpu_ctx->func_sim->g_pc_to_finfo[PC] = this;
m_instr_mem[n] = pI;
- s_g_pc_to_insn.push_back(pI);
- assert(pI == s_g_pc_to_insn[PC]);
+ gpgpu_ctx->s_g_pc_to_insn.push_back(pI);
+ assert(pI == gpgpu_ctx->s_g_pc_to_insn[PC]);
pI->set_m_instr_mem_index(n);
pI->set_PC(PC);
assert( pI->inst_size() <= MAX_INST_SIZE );
for( unsigned i=1; i < pI->inst_size(); i++ ) {
- s_g_pc_to_insn.push_back((ptx_instruction*)NULL);
+ gpgpu_ctx->s_g_pc_to_insn.push_back((ptx_instruction*)NULL);
m_instr_mem[n+i]=NULL;
}
n += pI->inst_size();
PC += pI->inst_size();
}
}
- g_assemble_code_next_pc=PC;
+ gpgpu_ctx->func_sim->g_assemble_code_next_pc=PC;
for ( unsigned ii=0; ii < n; ii += m_instr_mem[ii]->inst_size() ) { // handle branch instructions
ptx_instruction *pI = m_instr_mem[ii];
if ( pI->get_opcode() == BRA_OP || pI->get_opcode() == BREAKADDR_OP || pI->get_opcode() == CALLP_OP) {
@@ -446,8 +428,8 @@ void gpgpu_t::memcpy_to_gpu( size_t dst_start_addr, const void *src, size_t coun
m_global_mem->write(dst_start_addr+n,1, src_data+n,NULL,NULL);
// Copy into the performance model.
- extern gpgpu_sim* g_the_gpu;
- g_the_gpu->perf_memcpy_to_gpu(dst_start_addr, count);
+ //extern gpgpu_sim* g_the_gpu;
+ g_the_gpu()->perf_memcpy_to_gpu(dst_start_addr, count);
if(g_debug_execution >= 3) {
printf( " done.\n");
fflush(stdout);
@@ -465,8 +447,8 @@ void gpgpu_t::memcpy_from_gpu( void *dst, size_t src_start_addr, size_t count )
m_global_mem->read(src_start_addr+n,1,dst_data+n);
// Copy into the performance model.
- extern gpgpu_sim* g_the_gpu;
- g_the_gpu->perf_memcpy_to_gpu(src_start_addr, count);
+ //extern gpgpu_sim* g_the_gpu;
+ g_the_gpu()->perf_memcpy_to_gpu(src_start_addr, count);
if(g_debug_execution >= 3) {
printf( " done.\n");
fflush(stdout);
@@ -507,7 +489,7 @@ void gpgpu_t::gpu_memset( size_t dst_start_addr, int c, size_t count )
}
}
-void ptx_print_insn( address_type pc, FILE *fp )
+void cuda_sim::ptx_print_insn( address_type pc, FILE *fp )
{
std::map<unsigned,function_info*>::iterator f = g_pc_to_finfo.find(pc);
if( f == g_pc_to_finfo.end() ) {
@@ -519,7 +501,7 @@ void ptx_print_insn( address_type pc, FILE *fp )
finfo->print_insn(pc,fp);
}
-std::string ptx_get_insn_str( address_type pc )
+std::string cuda_sim::ptx_get_insn_str( address_type pc )
{
std::map<unsigned,function_info*>::iterator f = g_pc_to_finfo.find(pc);
if( f == g_pc_to_finfo.end() ) {
@@ -665,35 +647,38 @@ void ptx_instruction::set_opcode_and_latency()
* [3] MAD
* [4] DIV
*/
- sscanf(opcode_latency_int, "%u,%u,%u,%u,%u",
+ sscanf(gpgpu_ctx->func_sim->opcode_latency_int, "%u,%u,%u,%u,%u",
&int_latency[0],&int_latency[1],&int_latency[2],
&int_latency[3],&int_latency[4]);
- sscanf(opcode_latency_fp, "%u,%u,%u,%u,%u",
+ sscanf(gpgpu_ctx->func_sim->opcode_latency_fp, "%u,%u,%u,%u,%u",
&fp_latency[0],&fp_latency[1],&fp_latency[2],
&fp_latency[3],&fp_latency[4]);
- sscanf(opcode_latency_dp, "%u,%u,%u,%u,%u",
+ sscanf(gpgpu_ctx->func_sim->opcode_latency_dp, "%u,%u,%u,%u,%u",
&dp_latency[0],&dp_latency[1],&dp_latency[2],
&dp_latency[3],&dp_latency[4]);
- sscanf(opcode_latency_sfu, "%u",
+ sscanf(gpgpu_ctx->func_sim->opcode_latency_sfu, "%u",
&sfu_latency);
- sscanf(opcode_latency_tensor, "%u",
+ sscanf(gpgpu_ctx->func_sim->opcode_latency_tensor, "%u",
&tensor_latency);
- sscanf(opcode_initiation_int, "%u,%u,%u,%u,%u",
+ sscanf(gpgpu_ctx->func_sim->opcode_initiation_int, "%u,%u,%u,%u,%u",
&int_init[0],&int_init[1],&int_init[2],
&int_init[3],&int_init[4]);
- sscanf(opcode_initiation_fp, "%u,%u,%u,%u,%u",
+ sscanf(gpgpu_ctx->func_sim->opcode_initiation_fp, "%u,%u,%u,%u,%u",
&fp_init[0],&fp_init[1],&fp_init[2],
&fp_init[3],&fp_init[4]);
- sscanf(opcode_initiation_dp, "%u,%u,%u,%u,%u",
+ sscanf(gpgpu_ctx->func_sim->opcode_initiation_dp, "%u,%u,%u,%u,%u",
&dp_init[0],&dp_init[1],&dp_init[2],
&dp_init[3],&dp_init[4]);
- sscanf(opcode_initiation_sfu, "%u",
+ sscanf(gpgpu_ctx->func_sim->opcode_initiation_sfu, "%u",
&sfu_init);
- sscanf(opcode_initiation_tensor, "%u",
+ sscanf(gpgpu_ctx->func_sim->opcode_initiation_tensor, "%u",
&tensor_init);
- sscanf(cdp_latency_str, "%u,%u,%u,%u,%u",
- &cdp_latency[0],&cdp_latency[1],&cdp_latency[2],
- &cdp_latency[3],&cdp_latency[4]);
+ sscanf(gpgpu_ctx->func_sim->cdp_latency_str, "%u,%u,%u,%u,%u",
+ &gpgpu_ctx->func_sim->cdp_latency[0],
+ &gpgpu_ctx->func_sim->cdp_latency[1],
+ &gpgpu_ctx->func_sim->cdp_latency[2],
+ &gpgpu_ctx->func_sim->cdp_latency[3],
+ &gpgpu_ctx->func_sim->cdp_latency[4]);
if(!m_operands.empty()){
std::vector<operand_info>::iterator it;
@@ -1102,7 +1087,7 @@ void ptx_instruction::pre_decode()
}
// get reconvergence pc
- reconvergence_pc = get_converge_point(pc);
+ reconvergence_pc = gpgpu_ctx->func_sim->get_converge_point(pc);
m_decoded=true;
}
@@ -1268,8 +1253,8 @@ void function_info::finalize( memory_space *param_mem )
void function_info::param_to_shared( memory_space *shared_mem, symbol_table *symtab )
{
// TODO: call this only for PTXPlus with GT200 models
- extern gpgpu_sim* g_the_gpu;
- if (not g_the_gpu->get_config().convert_to_ptxplus()) return;
+ //extern gpgpu_sim* g_the_gpu;
+ if (not g_the_gpu()->get_config().convert_to_ptxplus()) return;
// copies parameters into simulated shared memory
for( std::map<unsigned,param_info>::iterator i=m_ptx_kernel_param_info.begin(); i!=m_ptx_kernel_param_info.end(); i++ ) {
@@ -1466,7 +1451,7 @@ void function_info::ptx_jit_config(std::map<unsigned long long, size_t> mallocPt
}
template<int activate_level>
-bool ptx_debug_exec_dump_cond(int thd_uid, addr_t pc)
+bool cuda_sim::ptx_debug_exec_dump_cond(int thd_uid, addr_t pc)
{
if (g_debug_execution >= activate_level) {
// check each type of debug dump constraint to filter out dumps
@@ -1483,7 +1468,7 @@ bool ptx_debug_exec_dump_cond(int thd_uid, addr_t pc)
return false;
}
-void init_inst_classification_stat()
+void cuda_sim::init_inst_classification_stat()
{
static std::set<unsigned> init;
if( init.find(g_ptx_kernel_count) != init.end() )
@@ -1552,7 +1537,8 @@ void ptx_thread_info::ptx_exec_inst( warp_inst_t &inst, unsigned lane_id)
}
if ( g_debug_execution >= 6 || m_gpu->get_config().get_ptx_inst_debug_to_file()) {
- if ( (g_debug_thread_uid==0) || (get_uid() == (unsigned)g_debug_thread_uid) ) {
+ if ( (m_gpu->gpgpu_ctx->func_sim->g_debug_thread_uid==0)
+ || (get_uid() == (unsigned)(m_gpu->gpgpu_ctx->func_sim->g_debug_thread_uid)) ) {
clear_modifiedregs();
enable_debug_trace();
@@ -1624,11 +1610,11 @@ void ptx_thread_info::ptx_exec_inst( warp_inst_t &inst, unsigned lane_id)
fflush(m_gpu->get_ptx_inst_debug_file());
}
- if ( ptx_debug_exec_dump_cond<5>(get_uid(), pc) ) {
+ if ( m_gpu->gpgpu_ctx->func_sim->ptx_debug_exec_dump_cond<5>(get_uid(), pc) ) {
dim3 ctaid = get_ctaid();
dim3 tid = get_tid();
printf("%u [thd=%u][i=%u] : ctaid=(%u,%u,%u) tid=(%u,%u,%u) icount=%u [pc=%u] (%s:%u - %s) [0x%llx]\n",
- g_ptx_sim_num_insn,
+ m_gpu->gpgpu_ctx->func_sim->g_ptx_sim_num_insn,
get_uid(),
pI->uid(), ctaid.x,ctaid.y,ctaid.z,tid.x,tid.y,tid.z,
get_icount(),
@@ -1678,22 +1664,22 @@ void ptx_thread_info::ptx_exec_inst( warp_inst_t &inst, unsigned lane_id)
}
if ( g_debug_execution >= 6 ) {
- if ( ptx_debug_exec_dump_cond<6>(get_uid(), pc) )
+ if ( m_gpu->gpgpu_ctx->func_sim->ptx_debug_exec_dump_cond<6>(get_uid(), pc) )
dump_modifiedregs(stdout);
}
if ( g_debug_execution >= 10 ) {
- if ( ptx_debug_exec_dump_cond<10>(get_uid(), pc) )
+ if ( m_gpu->gpgpu_ctx->func_sim->ptx_debug_exec_dump_cond<10>(get_uid(), pc) )
dump_regs(stdout);
}
update_pc();
- g_ptx_sim_num_insn++;
+ m_gpu->gpgpu_ctx->func_sim->g_ptx_sim_num_insn++;
//not using it with functional simulation mode
if(!(this->m_functionalSimulationMode))
ptx_file_line_stats_add_exec_count(pI);
- if ( gpgpu_ptx_instruction_classification ) {
- init_inst_classification_stat();
+ if ( m_gpu->gpgpu_ctx->func_sim->gpgpu_ptx_instruction_classification ) {
+ m_gpu->gpgpu_ctx->func_sim->init_inst_classification_stat();
unsigned space_type=0;
switch ( pI->get_space().get_type() ) {
case global_space: space_type = 10; break;
@@ -1709,15 +1695,15 @@ void ptx_thread_info::ptx_exec_inst( warp_inst_t &inst, unsigned lane_id)
space_type = 0 ;
break;
}
- StatAddSample( g_inst_classification_stat[g_ptx_kernel_count], op_classification);
- if (space_type) StatAddSample( g_inst_classification_stat[g_ptx_kernel_count], ( int )space_type);
- StatAddSample( g_inst_op_classification_stat[g_ptx_kernel_count], (int) pI->get_opcode() );
+ StatAddSample( m_gpu->gpgpu_ctx->func_sim->g_inst_classification_stat[m_gpu->gpgpu_ctx->func_sim->g_ptx_kernel_count], op_classification);
+ if (space_type) StatAddSample( m_gpu->gpgpu_ctx->func_sim->g_inst_classification_stat[m_gpu->gpgpu_ctx->func_sim->g_ptx_kernel_count], ( int )space_type);
+ StatAddSample( m_gpu->gpgpu_ctx->func_sim->g_inst_op_classification_stat[m_gpu->gpgpu_ctx->func_sim->g_ptx_kernel_count], (int) pI->get_opcode() );
}
- if ( (g_ptx_sim_num_insn % 100000) == 0 ) {
+ if ( (m_gpu->gpgpu_ctx->func_sim->g_ptx_sim_num_insn % 100000) == 0 ) {
dim3 ctaid = get_ctaid();
dim3 tid = get_tid();
DPRINTF(LIVENESS, "GPGPU-Sim PTX: %u instructions simulated : ctaid=(%u,%u,%u) tid=(%u,%u,%u)\n",
- g_ptx_sim_num_insn, ctaid.x,ctaid.y,ctaid.z,tid.x,tid.y,tid.z );
+ m_gpu->gpgpu_ctx->func_sim->g_ptx_sim_num_insn, ctaid.x,ctaid.y,ctaid.z,tid.x,tid.y,tid.z );
fflush(stdout);
}
@@ -1740,7 +1726,7 @@ void ptx_thread_info::ptx_exec_inst( warp_inst_t &inst, unsigned lane_id)
}
-void set_param_gpgpu_num_shaders(int num_shaders)
+void cuda_sim::set_param_gpgpu_num_shaders(int num_shaders)
{
gpgpu_param_num_shaders = num_shaders;
}
@@ -1750,9 +1736,9 @@ const struct gpgpu_ptx_sim_info* ptx_sim_kernel_info(const function_info *kernel
return kernel->get_kernel_info();
}
-const warp_inst_t *ptx_fetch_inst( address_type pc )
+const warp_inst_t *gpgpu_context::ptx_fetch_inst( address_type pc )
{
- return function_info::pc_to_instruction(pc);
+ return pc_to_instruction(pc);
}
unsigned ptx_sim_init_thread( kernel_info_t &kernel,
@@ -1822,7 +1808,7 @@ unsigned ptx_sim_init_thread( kernel_info_t &kernel,
assert( max_cta_per_sm > 0 );
//unsigned sm_idx = (tid/cta_size)*gpgpu_param_num_shaders + sid;
- unsigned sm_idx = hw_cta_id*gpgpu_param_num_shaders + sid;
+ unsigned sm_idx = hw_cta_id*gpu->gpgpu_ctx->func_sim->gpgpu_param_num_shaders + sid;
if ( shared_memory_lookup.find(sm_idx) == shared_memory_lookup.end() ) {
if ( g_debug_execution >= 1 ) {
@@ -1836,7 +1822,7 @@ unsigned ptx_sim_init_thread( kernel_info_t &kernel,
snprintf(buf,512,"sstarr_%u", sid);
sstarr_mem = new memory_space_impl<16*1024>(buf,4);
sstarr_memory_lookup[sm_idx] = sstarr_mem;
- cta_info = new ptx_cta_info(sm_idx);
+ cta_info = new ptx_cta_info(sm_idx, gpu->gpgpu_ctx);
ptx_cta_lookup[sm_idx] = cta_info;
} else {
if ( g_debug_execution >= 1 ) {
@@ -1920,7 +1906,7 @@ size_t get_kernel_code_size( class function_info *entry )
}
-kernel_info_t *gpgpu_opencl_ptx_sim_init_grid(class function_info *entry,
+kernel_info_t *cuda_sim::gpgpu_opencl_ptx_sim_init_grid(class function_info *entry,
gpgpu_ptx_sim_arg_list_t args,
struct dim3 gridDim,
struct dim3 blockDim,
@@ -1952,38 +1938,33 @@ void print_splash()
}
}
-std::map<const void*,std::string> g_const_name_lookup; // indexed by hostVar
-std::map<const void*,std::string> g_global_name_lookup; // indexed by hostVar
-std::set<std::string> g_globals;
-std::set<std::string> g_constants;
-
-void gpgpu_ptx_sim_register_const_variable(void *hostVar, const char *deviceName, size_t size )
+void cuda_sim::gpgpu_ptx_sim_register_const_variable(void *hostVar, const char *deviceName, size_t size )
{
printf("GPGPU-Sim PTX registering constant %s (%zu bytes) to name mapping\n", deviceName, size );
g_const_name_lookup[hostVar] = deviceName;
}
-void gpgpu_ptx_sim_register_global_variable(void *hostVar, const char *deviceName, size_t size )
+void cuda_sim::gpgpu_ptx_sim_register_global_variable(void *hostVar, const char *deviceName, size_t size )
{
printf("GPGPU-Sim PTX registering global %s hostVar to name mapping\n", deviceName );
g_global_name_lookup[hostVar] = deviceName;
}
-void gpgpu_ptx_sim_memcpy_symbol(const char *hostVar, const void *src, size_t count, size_t offset, int to, gpgpu_t *gpu )
+void cuda_sim::gpgpu_ptx_sim_memcpy_symbol(const char *hostVar, const void *src, size_t count, size_t offset, int to, gpgpu_t *gpu )
{
printf("GPGPU-Sim PTX: starting gpgpu_ptx_sim_memcpy_symbol with hostVar 0x%p\n", hostVar);
bool found_sym = false;
memory_space_t mem_region = undefined_space;
std::string sym_name;
- std::map<const void*,std::string>::iterator c=g_const_name_lookup.find(hostVar);
- if ( c!=g_const_name_lookup.end() ) {
+ std::map<const void*,std::string>::iterator c=gpu->gpgpu_ctx->func_sim->g_const_name_lookup.find(hostVar);
+ if ( c!=gpu->gpgpu_ctx->func_sim->g_const_name_lookup.end() ) {
found_sym = true;
sym_name = c->second;
mem_region = const_space;
}
- std::map<const void*,std::string>::iterator g=g_global_name_lookup.find(hostVar);
- if ( g!=g_global_name_lookup.end() ) {
+ std::map<const void*,std::string>::iterator g=gpu->gpgpu_ctx->func_sim->g_global_name_lookup.find(hostVar);
+ if ( g!=gpu->gpgpu_ctx->func_sim->g_global_name_lookup.end() ) {
if ( found_sym ) {
printf("Execution error: PTX symbol \"%s\" w/ hostVar=0x%Lx is declared both const and global?\n",
sym_name.c_str(), (unsigned long long)hostVar );
@@ -2011,8 +1992,8 @@ void gpgpu_ptx_sim_memcpy_symbol(const char *hostVar, const void *src, size_t co
const char *mem_name = NULL;
memory_space *mem = NULL;
- std::map<std::string,symbol_table*>::iterator st = g_sym_name_to_symbol_table.find(sym_name.c_str());
- assert( st != g_sym_name_to_symbol_table.end() );
+ std::map<std::string,symbol_table*>::iterator st = gpgpu_ctx->ptx_parser->g_sym_name_to_symbol_table.find(sym_name.c_str());
+ assert( st != gpgpu_ctx->ptx_parser->g_sym_name_to_symbol_table.end() );
symbol_table *symtab = st->second;
symbol *sym = symtab->lookup(sym_name.c_str());
@@ -2039,13 +2020,9 @@ void gpgpu_ptx_sim_memcpy_symbol(const char *hostVar, const void *src, size_t co
fflush(stdout);
}
-int g_ptx_sim_mode; // if non-zero run functional simulation only (i.e., no notion of a clock cycle)
-
extern int ptx_debug;
-bool g_cuda_launch_blocking = false;
-
-void read_sim_environment_variables()
+void cuda_sim::read_sim_environment_variables()
{
ptx_debug = 0;
g_debug_execution = 0;
@@ -2103,8 +2080,6 @@ void read_sim_environment_variables()
}
}
-ptx_cta_info *g_func_cta_info = NULL;
-
#define MAX(a,b) (((a)>(b))?(a):(b))
unsigned max_cta (const struct gpgpu_ptx_sim_info *kernel_info, unsigned threads_per_cta, unsigned int warp_size, unsigned int n_thread_per_shader, unsigned int gpgpu_shmem_size, unsigned int gpgpu_shader_registers, unsigned int max_cta_per_core)
@@ -2143,12 +2118,12 @@ unsigned max_cta (const struct gpgpu_ptx_sim_info *kernel_info, unsigned threads
This function simulates the CUDA code functionally, it takes a kernel_info_t parameter
which holds the data for the CUDA kernel to be executed
!*/
-void gpgpu_cuda_ptx_sim_main_func( kernel_info_t &kernel, bool openCL )
+void cuda_sim::gpgpu_cuda_ptx_sim_main_func( kernel_info_t &kernel, bool openCL )
{
printf("GPGPU-Sim: Performing Functional Simulation, executing kernel %s...\n",kernel.name().c_str());
//using a shader core object for book keeping, it is not needed but as most function built for performance simulation need it we use it here
- extern gpgpu_sim *g_the_gpu;
+ //extern gpgpu_sim *g_the_gpu;
//before we execute, we should do PDOM analysis for functional simulation scenario.
function_info *kernel_func_info = kernel.entry();
const struct gpgpu_ptx_sim_info *kernel_info = ptx_sim_kernel_info(kernel_func_info);
@@ -2163,7 +2138,7 @@ void gpgpu_cuda_ptx_sim_main_func( kernel_info_t &kernel, bool openCL )
kernel_func_info->set_pdom();
}
- unsigned max_cta_tot = max_cta(kernel_info,kernel.threads_per_cta(), g_the_gpu->getShaderCoreConfig()->warp_size, g_the_gpu->getShaderCoreConfig()->n_thread_per_shader, g_the_gpu->getShaderCoreConfig()->gpgpu_shmem_size, g_the_gpu->getShaderCoreConfig()->gpgpu_shader_registers, g_the_gpu->getShaderCoreConfig()->max_cta_per_core);
+ unsigned max_cta_tot = max_cta(kernel_info,kernel.threads_per_cta(), g_the_gpu()->getShaderCoreConfig()->warp_size, g_the_gpu()->getShaderCoreConfig()->n_thread_per_shader, g_the_gpu()->getShaderCoreConfig()->gpgpu_shmem_size, g_the_gpu()->getShaderCoreConfig()->gpgpu_shader_registers, g_the_gpu()->getShaderCoreConfig()->max_cta_per_core);
printf("Max CTA : %d\n",max_cta_tot);
@@ -2171,11 +2146,11 @@ void gpgpu_cuda_ptx_sim_main_func( kernel_info_t &kernel, bool openCL )
int inst_count=50;
- int cp_op= g_the_gpu->checkpoint_option;
- int cp_CTA = g_the_gpu->checkpoint_CTA;
- int cp_kernel= g_the_gpu->checkpoint_kernel;
- cp_count= g_the_gpu->checkpoint_insn_Y;
- cp_cta_resume= g_the_gpu->checkpoint_CTA_t;
+ int cp_op= g_the_gpu()->checkpoint_option;
+ int cp_CTA = g_the_gpu()->checkpoint_CTA;
+ int cp_kernel= g_the_gpu()->checkpoint_kernel;
+ cp_count= g_the_gpu()->checkpoint_insn_Y;
+ cp_cta_resume= g_the_gpu()->checkpoint_CTA_t;
int cta_launched =0;
//we excute the kernel one CTA (Block) at the time, as synchronization functions work block wise
@@ -2187,13 +2162,13 @@ void gpgpu_cuda_ptx_sim_main_func( kernel_info_t &kernel, bool openCL )
{
functionalCoreSim cta(
&kernel,
- g_the_gpu,
- g_the_gpu->getShaderCoreConfig()->warp_size
+ g_the_gpu(),
+ g_the_gpu()->getShaderCoreConfig()->warp_size
);
cta.execute(cp_count,temp);
#if (CUDART_VERSION >= 5000)
- launch_all_device_kernels();
+ gpgpu_ctx->device_runtime->launch_all_device_kernels();
#endif
}
else
@@ -2209,7 +2184,7 @@ void gpgpu_cuda_ptx_sim_main_func( kernel_info_t &kernel, bool openCL )
{
char f1name[2048];
snprintf(f1name,2048,"checkpoint_files/global_mem_%d.txt", kernel.get_uid() );
- g_checkpoint->store_global_mem(g_the_gpu->get_global_memory(), f1name , "%08x");
+ g_checkpoint->store_global_mem(g_the_gpu()->get_global_memory(), f1name , "%08x");
}
@@ -2219,8 +2194,8 @@ void gpgpu_cuda_ptx_sim_main_func( kernel_info_t &kernel, bool openCL )
//openCL kernel simulation calls don't register the kernel so we don't register its exit
if(!openCL) {
- extern stream_manager *g_stream_manager;
- g_stream_manager->register_finished_kernel(kernel.get_uid());
+ //extern stream_manager *g_stream_manager;
+ g_stream_manager()->register_finished_kernel(kernel.get_uid());
}
//******PRINTING*******
@@ -2235,7 +2210,7 @@ void gpgpu_cuda_ptx_sim_main_func( kernel_info_t &kernel, bool openCL )
//g_simulation_starttime is initilized by gpgpu_ptx_sim_init_perf() in gpgpusim_entrypoint.cc upon starting gpgpu-sim
time_t end_time, elapsed_time, days, hrs, minutes, sec;
end_time = time((time_t *)NULL);
- elapsed_time = MAX(end_time - g_simulation_starttime, 1);
+ elapsed_time = MAX(end_time - GPGPUsim_ctx_ptr()->g_simulation_starttime, 1);
//calculating and printing simulation time in terms of days, hours, minutes and seconds
@@ -2269,7 +2244,7 @@ void functionalCoreSim::initializeCTA(unsigned ctaid_cp)
assert(m_thread[i]!=NULL && !m_thread[i]->is_done());
char fname[2048];
snprintf(fname,2048,"checkpoint_files/thread_%d_0_reg.txt",i );
- if(cp_cta_resume==1)
+ if(m_gpu->gpgpu_ctx->func_sim->cp_cta_resume==1)
m_thread[i]->resume_reg_thread(fname,symtab);
ctaLiveThreads++;
}
@@ -2293,7 +2268,7 @@ void functionalCoreSim::createWarp(unsigned warpId)
char fname[2048];
snprintf(fname,2048,"checkpoint_files/warp_%d_0_simt.txt",warpId );
- if(cp_cta_resume==1)
+ if(m_gpu->gpgpu_ctx->func_sim->cp_cta_resume==1)
{
unsigned pc,rpc;
m_simt_stack[warpId]->resume(fname);
@@ -2309,8 +2284,8 @@ void functionalCoreSim::createWarp(unsigned warpId)
void functionalCoreSim::execute(int inst_count, unsigned ctaid_cp)
{
- cp_count= m_gpu->checkpoint_insn_Y;
- cp_cta_resume= m_gpu->checkpoint_CTA_t;
+ m_gpu->gpgpu_ctx->func_sim->cp_count= m_gpu->checkpoint_insn_Y;
+ m_gpu->gpgpu_ctx->func_sim->cp_cta_resume= m_gpu->checkpoint_CTA_t;
initializeCTA(ctaid_cp);
int count=0;
@@ -2389,11 +2364,11 @@ void functionalCoreSim::executeWarp(unsigned i, bool &allAtBarrier, bool & someO
if(!m_warpAtBarrier[i]&& m_liveThreadCount[i]>0) allAtBarrier = false;
}
-unsigned translate_pc_to_ptxlineno(unsigned pc)
+unsigned gpgpu_context::translate_pc_to_ptxlineno(unsigned pc)
{
// this function assumes that the kernel fits inside a single PTX file
// function_info *pFunc = g_func_info; // assume that the current kernel is the one in query
- const ptx_instruction *pInsn = function_info::pc_to_instruction(pc);
+ const ptx_instruction *pInsn = pc_to_instruction(pc);
unsigned ptx_line_number = pInsn->source_line();
return ptx_line_number;
@@ -2403,8 +2378,6 @@ unsigned translate_pc_to_ptxlineno(unsigned pc)
extern std::map<unsigned,const char*> get_duplicate();
-int g_ptxinfo_error_detected;
-
static char *g_ptxinfo_kname = NULL;
static struct gpgpu_ptx_sim_info g_ptxinfo;
static std::map<unsigned,const char*> g_duplicate;
@@ -2532,14 +2505,7 @@ void ptxinfo_opencl_addinfo( std::map<std::string,function_info*> &kernels )
clear_ptxinfo();
}
-struct rec_pts {
- gpgpu_recon_t *s_kernel_recon_points;
- int s_num_recon;
-};
-
-class std::map<function_info*,rec_pts> g_rpts;
-
-struct rec_pts find_reconvergence_points( function_info *finfo )
+struct rec_pts cuda_sim::find_reconvergence_points( function_info *finfo )
{
rec_pts tmp;
std::map<function_info*,rec_pts>::iterator r=g_rpts.find(finfo);
@@ -2578,7 +2544,7 @@ address_type get_return_pc( void *thd )
return the_thread->get_return_PC();
}
-address_type get_converge_point( address_type pc )
+address_type cuda_sim::get_converge_point( address_type pc )
{
// the branch could encode the reconvergence point and/or a bit that indicates the
// reconvergence point is the return PC on the call stack in the case the branch has
diff --git a/src/cuda-sim/cuda-sim.h b/src/cuda-sim/cuda-sim.h
index e690356..1be3d19 100644
--- a/src/cuda-sim/cuda-sim.h
+++ b/src/cuda-sim/cuda-sim.h
@@ -36,33 +36,16 @@
#include <string>
#include"ptx_sim.h"
+class gpgpu_context;
class memory_space;
class function_info;
class symbol_table;
extern const char *g_gpgpusim_version_string;
-extern int g_ptx_sim_mode;
extern int g_debug_execution;
-extern int g_debug_thread_uid;
-extern void ** g_inst_classification_stat;
-extern void ** g_inst_op_classification_stat;
-extern int g_ptx_kernel_count; // used for classification stat collection purposes
-extern char *opcode_latency_int, *opcode_latency_fp, *opcode_latency_dp,*opcode_latency_sfu,*opcode_latency_tensor;
-
-void ptx_opcocde_latency_options (option_parser_t opp);
-extern class kernel_info_t *gpgpu_opencl_ptx_sim_init_grid(class function_info *entry,
- gpgpu_ptx_sim_arg_list_t args,
- struct dim3 gridDim,
- struct dim3 blockDim,
- class gpgpu_t *gpu );
-extern void gpgpu_cuda_ptx_sim_main_func( kernel_info_t &kernel, bool openCL = false );
extern void print_splash();
-extern void gpgpu_ptx_sim_register_const_variable(void*, const char *deviceName, size_t size );
-extern void gpgpu_ptx_sim_register_global_variable(void *hostVar, const char *deviceName, size_t size );
-extern void gpgpu_ptx_sim_memcpy_symbol(const char *hostVar, const void *src, size_t count, size_t offset, int to, gpgpu_t *gpu );
-extern void read_sim_environment_variables();
extern void ptxinfo_opencl_addinfo( std::map<std::string,function_info*> &kernels );
unsigned ptx_sim_init_thread( kernel_info_t &kernel,
class ptx_thread_info** thread_info,
@@ -75,12 +58,7 @@ unsigned ptx_sim_init_thread( kernel_info_t &kernel,
unsigned hw_warp_id,
gpgpu_t *gpu,
bool functionalSimulationMode = false);
-const warp_inst_t *ptx_fetch_inst( address_type pc );
const struct gpgpu_ptx_sim_info* ptx_sim_kernel_info(const class function_info *kernel);
-void ptx_print_insn( address_type pc, FILE *fp );
-std::string ptx_get_insn_str( address_type pc );
-void set_param_gpgpu_num_shaders(int num_shaders);
-
/*!
* This class functionally executes a kernel. It uses the basic data structures and procedures in core_t
@@ -134,4 +112,91 @@ void print_ptxinfo();
void clear_ptxinfo();
struct gpgpu_ptx_sim_info get_ptxinfo();
+class gpgpu_recon_t;
+struct rec_pts {
+ gpgpu_recon_t *s_kernel_recon_points;
+ int s_num_recon;
+};
+
+
+class cuda_sim {
+ public:
+ cuda_sim( gpgpu_context* ctx ) {
+ g_ptx_sim_num_insn = 0;
+ g_ptx_kernel_count = -1; // used for classification stat collection purposes
+ gpgpu_param_num_shaders = 0;
+ g_cuda_launch_blocking = false;
+ g_inst_classification_stat = NULL;
+ g_inst_op_classification_stat= NULL;
+ g_assemble_code_next_pc=0;
+ g_debug_thread_uid = 0;
+ g_override_embedded_ptx = false;
+ ptx_tex_regs = NULL;
+ g_ptx_thread_info_delete_count=0;
+ g_ptx_thread_info_uid_next=1;
+ g_debug_pc = 0xBEEF1518;
+ gpgpu_ctx = ctx;
+ }
+ //global variables
+ char *opcode_latency_int;
+ char *opcode_latency_fp;
+ char *opcode_latency_dp;
+ char *opcode_latency_sfu;
+ char *opcode_latency_tensor;
+ char *opcode_initiation_int;
+ char *opcode_initiation_fp;
+ char *opcode_initiation_dp;
+ char *opcode_initiation_sfu;
+ char *opcode_initiation_tensor;
+ int cp_count;
+ int cp_cta_resume;
+ int g_ptxinfo_error_detected;
+ unsigned g_ptx_sim_num_insn;
+ char *cdp_latency_str;
+ int g_ptx_kernel_count; // used for classification stat collection purposes
+ std::map<const void*,std::string> g_global_name_lookup; // indexed by hostVar
+ std::map<const void*,std::string> g_const_name_lookup; // indexed by hostVar
+ int g_ptx_sim_mode; // if non-zero run functional simulation only (i.e., no notion of a clock cycle)
+ unsigned gpgpu_param_num_shaders;
+ class std::map<function_info*,rec_pts> g_rpts;
+ bool g_cuda_launch_blocking;
+ void ** g_inst_classification_stat;
+ void ** g_inst_op_classification_stat;
+ std::set<std::string> g_globals;
+ std::set<std::string> g_constants;
+ std::map<unsigned,function_info*> g_pc_to_finfo;
+ int gpgpu_ptx_instruction_classification;
+ unsigned cdp_latency[5];
+ unsigned g_assemble_code_next_pc;
+ int g_debug_thread_uid;
+ bool g_override_embedded_ptx;
+ std::set<unsigned long long> g_ptx_cta_info_sm_idx_used;
+ ptx_reg_t* ptx_tex_regs;
+ unsigned g_ptx_thread_info_delete_count;
+ unsigned g_ptx_thread_info_uid_next;
+ addr_t g_debug_pc;
+ // backward pointer
+ class gpgpu_context* gpgpu_ctx;
+ //global functions
+ void ptx_opcocde_latency_options (option_parser_t opp);
+ void gpgpu_cuda_ptx_sim_main_func( kernel_info_t &kernel, bool openCL = false );
+ int gpgpu_opencl_ptx_sim_main_func( kernel_info_t *grid );
+ void init_inst_classification_stat();
+ kernel_info_t *gpgpu_opencl_ptx_sim_init_grid(class function_info *entry,
+ gpgpu_ptx_sim_arg_list_t args,
+ struct dim3 gridDim,
+ struct dim3 blockDim,
+ gpgpu_t *gpu );
+ void gpgpu_ptx_sim_register_global_variable(void *hostVar, const char *deviceName, size_t size );
+ void gpgpu_ptx_sim_register_const_variable(void*, const char *deviceName, size_t size );
+ void read_sim_environment_variables();
+ void set_param_gpgpu_num_shaders(int num_shaders);
+ struct rec_pts find_reconvergence_points( function_info *finfo );
+ address_type get_converge_point( address_type pc );
+ void gpgpu_ptx_sim_memcpy_symbol(const char *hostVar, const void *src, size_t count, size_t offset, int to, gpgpu_t *gpu );
+ void ptx_print_insn( address_type pc, FILE *fp );
+ std::string ptx_get_insn_str( address_type pc );
+ template<int activate_level> bool ptx_debug_exec_dump_cond(int thd_uid, addr_t pc);
+};
+
#endif
diff --git a/src/cuda-sim/cuda_device_runtime.cc b/src/cuda-sim/cuda_device_runtime.cc
index 917e7a8..dc3adc3 100644
--- a/src/cuda-sim/cuda_device_runtime.cc
+++ b/src/cuda-sim/cuda_device_runtime.cc
@@ -5,8 +5,6 @@
#include <iostream>
#include <map>
-unsigned long long g_total_param_size = 0;
-unsigned long long g_max_total_param_size = 0;
#if (CUDART_VERSION >= 5000)
@@ -18,7 +16,9 @@ unsigned long long g_max_total_param_size = 0;
#include "cuda-sim.h"
#include "ptx_ir.h"
#include "../stream_manager.h"
+#include "../gpgpusim_entrypoint.h"
#include "cuda_device_runtime.h"
+#include "../../libcuda/gpgpu_context.h"
#define DEV_RUNTIME_REPORT(a) \
if( g_debug_execution ) { \
@@ -26,49 +26,12 @@ unsigned long long g_max_total_param_size = 0;
std::cout.flush(); \
}
-class device_launch_config_t {
-public:
- device_launch_config_t() {}
-
- device_launch_config_t(dim3 _grid_dim,
- dim3 _block_dim,
- unsigned int _shared_mem,
- function_info * _entry):
- grid_dim(_grid_dim),
- block_dim(_block_dim),
- shared_mem(_shared_mem),
- entry(_entry) {}
-
- dim3 grid_dim;
- dim3 block_dim;
- unsigned int shared_mem;
- function_info * entry;
-
-};
-
-class device_launch_operation_t {
-
-public:
- device_launch_operation_t() {}
- device_launch_operation_t(kernel_info_t *_grid,
- CUstream_st * _stream) :
- grid(_grid), stream(_stream) {}
-
- kernel_info_t * grid; //a new child grid
-
- CUstream_st * stream;
-
-};
-
-
-std::map<void *, device_launch_config_t> g_cuda_device_launch_param_map;
-std::list<device_launch_operation_t> g_cuda_device_launch_op;
-extern stream_manager *g_stream_manager;
+//extern stream_manager *g_stream_manager();
//Handling device runtime api:
//void * cudaGetParameterBufferV2(void *func, dim3 gridDimension, dim3 blockDimension, unsigned int sharedMemSize)
-void gpgpusim_cuda_getParameterBufferV2(const ptx_instruction * pI, ptx_thread_info * thread, const function_info * target_func)
+void cuda_device_runtime::gpgpusim_cuda_getParameterBufferV2(const ptx_instruction * pI, ptx_thread_info * thread, const function_info * target_func)
{
DEV_RUNTIME_REPORT("Calling cudaGetParameterBufferV2");
@@ -141,7 +104,7 @@ void gpgpusim_cuda_getParameterBufferV2(const ptx_instruction * pI, ptx_thread_i
//Handling device runtime api:
//cudaError_t cudaLaunchDeviceV2(void *parameterBuffer, cudaStream_t stream)
-void gpgpusim_cuda_launchDeviceV2(const ptx_instruction * pI, ptx_thread_info * thread, const function_info * target_func) {
+void cuda_device_runtime::gpgpusim_cuda_launchDeviceV2(const ptx_instruction * pI, ptx_thread_info * thread, const function_info * target_func) {
DEV_RUNTIME_REPORT("Calling cudaLaunchDeviceV2");
unsigned n_return = target_func->has_return();
@@ -200,7 +163,7 @@ void gpgpusim_cuda_launchDeviceV2(const ptx_instruction * pI, ptx_thread_info *
//create child kernel_info_t and index it with parameter_buffer address
gpgpu_t* gpu=thread->get_gpu();
device_grid = new kernel_info_t(config.grid_dim, config.block_dim, device_kernel_entry, gpu->getNameArrayMapping(), gpu->getNameInfoMapping());
- device_grid->launch_cycle = gpu_sim_cycle + gpu_tot_sim_cycle;
+ device_grid->launch_cycle = gpu->gpu_sim_cycle + gpu->gpu_tot_sim_cycle;
kernel_info_t & parent_grid = thread->get_kernel();
DEV_RUNTIME_REPORT("child kernel launched by " << parent_grid.name() << ", cta (" <<
thread->get_ctaid().x << ", " << thread->get_ctaid().y << ", " << thread->get_ctaid().z <<
@@ -262,7 +225,7 @@ void gpgpusim_cuda_launchDeviceV2(const ptx_instruction * pI, ptx_thread_info *
//Handling device runtime api:
//cudaError_t cudaStreamCreateWithFlags ( cudaStream_t* pStream, unsigned int flags)
//flags can only be cudaStreamNonBlocking
-void gpgpusim_cuda_streamCreateWithFlags(const ptx_instruction * pI, ptx_thread_info * thread, const function_info * target_func) {
+void cuda_device_runtime::gpgpusim_cuda_streamCreateWithFlags(const ptx_instruction * pI, ptx_thread_info * thread, const function_info * target_func) {
DEV_RUNTIME_REPORT("Calling cudaStreamCreateWithFlags");
unsigned n_return = target_func->has_return();
@@ -317,17 +280,17 @@ void gpgpusim_cuda_streamCreateWithFlags(const ptx_instruction * pI, ptx_thread_
}
-void launch_one_device_kernel() {
+void cuda_device_runtime::launch_one_device_kernel() {
if(!g_cuda_device_launch_op.empty()) {
device_launch_operation_t &op = g_cuda_device_launch_op.front();
- stream_operation stream_op = stream_operation(op.grid, g_ptx_sim_mode, op.stream);
- g_stream_manager->push(stream_op);
+ stream_operation stream_op = stream_operation(op.grid, gpgpu_ctx->func_sim->g_ptx_sim_mode, op.stream);
+ g_stream_manager()->push(stream_op);
g_cuda_device_launch_op.pop_front();
}
}
-void launch_all_device_kernels() {
+void cuda_device_runtime::launch_all_device_kernels() {
while(!g_cuda_device_launch_op.empty()) {
launch_one_device_kernel();
}
diff --git a/src/cuda-sim/cuda_device_runtime.h b/src/cuda-sim/cuda_device_runtime.h
index 6dbcd71..7f7a0ca 100644
--- a/src/cuda-sim/cuda_device_runtime.h
+++ b/src/cuda-sim/cuda_device_runtime.h
@@ -1,11 +1,68 @@
+#ifndef __cuda_device_runtime_h__
+#define __cuda_device_runtime_h__
//Jin: cuda_device_runtime.h
//Defines CUDA device runtime APIs for CDP support
+class device_launch_config_t {
+
+public:
+ device_launch_config_t() {}
+
+ device_launch_config_t(dim3 _grid_dim,
+ dim3 _block_dim,
+ unsigned int _shared_mem,
+ function_info * _entry):
+ grid_dim(_grid_dim),
+ block_dim(_block_dim),
+ shared_mem(_shared_mem),
+ entry(_entry) {}
+
+ dim3 grid_dim;
+ dim3 block_dim;
+ unsigned int shared_mem;
+ function_info * entry;
+
+};
+
+class device_launch_operation_t {
+
+public:
+ device_launch_operation_t() {}
+ device_launch_operation_t(kernel_info_t *_grid,
+ CUstream_st * _stream) :
+ grid(_grid), stream(_stream) {}
+
+ kernel_info_t * grid; //a new child grid
+
+ CUstream_st * stream;
+
+};
+
+class gpgpu_context;
+
+class cuda_device_runtime {
+ public:
+ cuda_device_runtime( gpgpu_context* ctx ) {
+ g_total_param_size = 0;
+ g_max_total_param_size = 0;
+ gpgpu_ctx = ctx;
+ }
+ unsigned long long g_total_param_size;
+ std::map<void *, device_launch_config_t> g_cuda_device_launch_param_map;
+ std::list<device_launch_operation_t> g_cuda_device_launch_op;
+ unsigned g_kernel_launch_latency;
+ unsigned long long g_max_total_param_size;
+ bool g_cdp_enabled;
+
+ // backward pointer
+ class gpgpu_context* gpgpu_ctx;
#if (CUDART_VERSION >= 5000)
#pragma once
-
-void gpgpusim_cuda_getParameterBufferV2(const ptx_instruction * pI, ptx_thread_info * thread, const function_info * target_func);
-void gpgpusim_cuda_launchDeviceV2(const ptx_instruction * pI, ptx_thread_info * thread, const function_info * target_func);
-void gpgpusim_cuda_streamCreateWithFlags(const ptx_instruction * pI, ptx_thread_info * thread, const function_info * target_func);
-void launch_all_device_kernels();
-void launch_one_device_kernel();
+ void gpgpusim_cuda_launchDeviceV2(const ptx_instruction * pI, ptx_thread_info * thread, const function_info * target_func);
+ void gpgpusim_cuda_streamCreateWithFlags(const ptx_instruction * pI, ptx_thread_info * thread, const function_info * target_func);
+ void gpgpusim_cuda_getParameterBufferV2(const ptx_instruction * pI, ptx_thread_info * thread, const function_info * target_func);
+ void launch_all_device_kernels();
+ void launch_one_device_kernel();
#endif
+};
+
+#endif /* __cuda_device_runtime_h__ */
diff --git a/src/cuda-sim/instructions.cc b/src/cuda-sim/instructions.cc
index 11001d7..58a077e 100644
--- a/src/cuda-sim/instructions.cc
+++ b/src/cuda-sim/instructions.cc
@@ -31,6 +31,8 @@
#include "ptx_ir.h"
#include "opcodes.h"
#include "ptx_sim.h"
+typedef void * yyscan_t;
+class ptx_recognizer;
#include "ptx.tab.h"
#include <stdlib.h>
#include <math.h>
@@ -54,10 +56,10 @@
#include "cuda_device_runtime.h"
#include <stdarg.h>
+#include "../../libcuda/gpgpu_context.h"
+
using half_float::half;
-unsigned ptx_instruction::g_num_ptx_inst_uid=0;
-bool debug_tensorcore = 0;
const char *g_opcode_string[NUM_OPCODES] = {
@@ -1526,6 +1528,7 @@ void bar_impl( const ptx_instruction *pIin, ptx_thread_info *thread )
op2_data = thread->get_operand_value(op2, op2, PRED_TYPE, thread, 1);
op2_data.u32=!(op2_data.pred & 0x0001);
pI->set_bar_id(op1_data.u32);
+ pI->set_bar_count(thread->get_ntid().x * thread->get_ntid().y * thread->get_ntid().z);
switch(red_op){
case ATOMIC_POPC:
thread->popc_reduction(ctaid,op1_data.u32,op2_data.u32);
@@ -1836,14 +1839,14 @@ void mma_impl( const ptx_instruction *pI, core_t *core, warp_inst_t inst )
for (thrd=0; thrd < core->get_warp_size(); thrd++){
thread = core->get_thread_info()[tid+thrd];
- if(debug_tensorcore)
+ if(core->get_gpu()->gpgpu_ctx->debug_tensorcore)
printf("THREAD=%d\n:",thrd);
for(int operand_num=1;operand_num<=3;operand_num++){
const operand_info &src_a= pI->operand_lookup(operand_num);
unsigned nelem = src_a.get_vect_nelem();
ptx_reg_t v[8];
thread->get_vector_operand_values( src_a, v, nelem );
- if(debug_tensorcore){
+ if(core->get_gpu()->gpgpu_ctx->debug_tensorcore){
printf("Thread%d_Iteration=%d\n:",thrd,operand_num);
for(k=0;k<nelem;k++){
printf("%x ",v[k].u64);
@@ -1865,14 +1868,14 @@ void mma_impl( const ptx_instruction *pI, core_t *core, warp_inst_t inst )
if(!((operand_num==3)&&(type2==F32_TYPE))){
for(k=0;k<2*nelem;k++){
temp=nw_v[k].f16;
- if(debug_tensorcore)
+ if(core->get_gpu()->gpgpu_ctx->debug_tensorcore)
printf("%.2f ",temp);
}
- if(debug_tensorcore)
+ if(core->get_gpu()->gpgpu_ctx->debug_tensorcore)
printf("\n");
}
else{
- if(debug_tensorcore){
+ if(core->get_gpu()->gpgpu_ctx->debug_tensorcore){
for(k=0;k<8;k++){
printf("%.2f ",v[k].f32);
}
@@ -1883,7 +1886,7 @@ void mma_impl( const ptx_instruction *pI, core_t *core, warp_inst_t inst )
case 1 ://operand 1
for(k=0;k<8;k++){
mapping(thrd,LOAD_A,a_layout,F16_TYPE,k,16,row,col,offset);
- if(debug_tensorcore)
+ if(core->get_gpu()->gpgpu_ctx->debug_tensorcore)
printf("A:thread=%d,row=%d,col=%d,offset=%d\n",thrd,row,col,offset);
matrix_a[row][col]=nw_v[offset];
}
@@ -1891,7 +1894,7 @@ void mma_impl( const ptx_instruction *pI, core_t *core, warp_inst_t inst )
case 2 ://operand 2
for(k=0;k<8;k++){
mapping(thrd,LOAD_B,b_layout,F16_TYPE,k,16,row,col,offset);
- if(debug_tensorcore)
+ if(core->get_gpu()->gpgpu_ctx->debug_tensorcore)
printf("B:thread=%d,row=%d,col=%d,offset=%d\n",thrd,row,col,offset);
matrix_b[row][col]=nw_v[offset];
}
@@ -1899,7 +1902,7 @@ void mma_impl( const ptx_instruction *pI, core_t *core, warp_inst_t inst )
case 3 ://operand 3
for(k=0;k<8;k++){
mapping(thrd,LOAD_C,ROW,type2,k,16,row,col,offset);
- if(debug_tensorcore)
+ if(core->get_gpu()->gpgpu_ctx->debug_tensorcore)
printf("C:thread=%d,row=%d,col=%d,offset=%d\n",thrd,row,col,offset);
if(type2!=F16_TYPE){
matrix_c[row][col]=v[offset];
@@ -1913,10 +1916,10 @@ void mma_impl( const ptx_instruction *pI, core_t *core, warp_inst_t inst )
printf("Invalid Operand Index\n" );
}
}
- if(debug_tensorcore)
+ if(core->get_gpu()->gpgpu_ctx->debug_tensorcore)
printf("\n");
}
- if(debug_tensorcore){
+ if(core->get_gpu()->gpgpu_ctx->debug_tensorcore){
printf("MATRIX_A\n");
for (i=0;i<16;i++){
for(j=0;j<16;j++){
@@ -1976,7 +1979,7 @@ void mma_impl( const ptx_instruction *pI, core_t *core, warp_inst_t inst )
}
}
}
- if(debug_tensorcore){
+ if(core->get_gpu()->gpgpu_ctx->debug_tensorcore){
printf("MATRIX_D\n");
for (i=0;i<16;i++){
for(j=0;j<16;j++){
@@ -1995,7 +1998,7 @@ void mma_impl( const ptx_instruction *pI, core_t *core, warp_inst_t inst )
int col_t[8];
for(k=0;k<8;k++){
mapping(thrd,LOAD_C,ROW,type,k,16,row_t[k],col_t[k],offset);
- if(debug_tensorcore)
+ if(core->get_gpu()->gpgpu_ctx->debug_tensorcore)
printf("mma:store:row:%d,col%d\n",row_t[k],col_t[k]);
}
thread = core->get_thread_info()[tid+thrd];
@@ -2004,7 +2007,7 @@ void mma_impl( const ptx_instruction *pI, core_t *core, warp_inst_t inst )
if(type==F32_TYPE){
thread->set_wmma_vector_operand_values(dst,matrix_d[row_t[0]][col_t[0]],matrix_d[row_t[1]][col_t[1]],matrix_d[row_t[2]][col_t[2]],matrix_d[row_t[3]][col_t[3]],matrix_d[row_t[4]][col_t[4]],matrix_d[row_t[5]][col_t[5]],matrix_d[row_t[6]][col_t[6]],matrix_d[row_t[7]][col_t[7]]);
- if(debug_tensorcore)
+ if(core->get_gpu()->gpgpu_ctx->debug_tensorcore)
{
printf("thread%d:",thrd);
for(k=0;k<8;k++){
@@ -2014,7 +2017,7 @@ void mma_impl( const ptx_instruction *pI, core_t *core, warp_inst_t inst )
}
}
else if(type==F16_TYPE){
- if(debug_tensorcore){
+ if(core->get_gpu()->gpgpu_ctx->debug_tensorcore){
printf("thread%d:",thrd);
for(k=0;k<8;k++){
temp=matrix_d[row_t[k]][col_t[k]].f16;
@@ -2034,7 +2037,7 @@ void mma_impl( const ptx_instruction *pI, core_t *core, warp_inst_t inst )
nw_data3.s64=((matrix_d[row_t[4]][col_t[4]].s64 & 0xffff))|((matrix_d[row_t[5]][col_t[5]].s64&0xffff)<<16);
nw_data4.s64=((matrix_d[row_t[6]][col_t[6]].s64 & 0xffff))|((matrix_d[row_t[7]][col_t[7]].s64&0xffff)<<16);
thread->set_vector_operand_values(dst,nw_data1,nw_data2,nw_data3,nw_data4);
- if(debug_tensorcore)
+ if(core->get_gpu()->gpgpu_ctx->debug_tensorcore)
printf("thread%d=%x,%x,%x,%x",thrd,nw_data1.s64,nw_data2.s64,nw_data3.s64,nw_data4.s64);
}
@@ -2092,15 +2095,15 @@ void call_impl( const ptx_instruction *pI, ptx_thread_info *thread )
#if (CUDART_VERSION >= 5000)
//Jin: handle device runtime apis for CDP
else if(fname == "cudaGetParameterBufferV2") {
- gpgpusim_cuda_getParameterBufferV2(pI, thread, target_func);
+ target_func->gpgpu_ctx->device_runtime->gpgpusim_cuda_getParameterBufferV2(pI, thread, target_func);
return;
}
else if(fname == "cudaLaunchDeviceV2") {
- gpgpusim_cuda_launchDeviceV2(pI, thread, target_func);
+ target_func->gpgpu_ctx->device_runtime->gpgpusim_cuda_launchDeviceV2(pI, thread, target_func);
return;
}
else if(fname == "cudaStreamCreateWithFlags") {
- gpgpusim_cuda_streamCreateWithFlags(pI, thread, target_func);
+ target_func->gpgpu_ctx->device_runtime->gpgpusim_cuda_streamCreateWithFlags(pI, thread, target_func);
return;
}
#endif
@@ -2300,12 +2303,12 @@ ptx_reg_t f2x( ptx_reg_t x, unsigned from_width, unsigned to_width, int to_sign,
half_float::half tmp_h;
//assert( from_width == 32);
- enum cuda_math::cudaRoundMode mode = cuda_math::cudaRoundZero;
+ enum cudaRoundMode mode = cudaRoundZero;
switch (rounding_mode) {
- case RZI_OPTION: mode = cuda_math::cudaRoundZero; break;
- case RNI_OPTION: mode = cuda_math::cudaRoundNearest; break;
- case RMI_OPTION: mode = cuda_math::cudaRoundMinInf; break;
- case RPI_OPTION: mode = cuda_math::cudaRoundPosInf; break;
+ case RZI_OPTION: mode = cudaRoundZero; break;
+ case RNI_OPTION: mode = cudaRoundNearest; break;
+ case RMI_OPTION: mode = cudaRoundMinInf; break;
+ case RPI_OPTION: mode = cudaRoundPosInf; break;
default: break;
}
@@ -3128,7 +3131,7 @@ void mma_st_impl( const ptx_instruction *pI, core_t *core, warp_inst_t &inst )
decode_space(space,thread,src1,mem,addr);
type_info_key::type_decode(type,size,t);
- if(debug_tensorcore)
+ if(core->get_gpu()->gpgpu_ctx->debug_tensorcore)
printf("mma_st: thrd=%d,addr=%x, fp(size=%d), stride=%d\n",thrd,addr_reg.u32,size,src2_data.u32);
addr_t new_addr = addr+thread_group_offset(thrd,wmma_type,wmma_layout,type,stride)*size/8;
addr_t push_addr;
@@ -3148,7 +3151,7 @@ void mma_st_impl( const ptx_instruction *pI, core_t *core, warp_inst_t &inst )
mem->write(push_addr,size/8,&v[k].s64,thread,pI);
mem_txn_addr[num_mem_txn++]=push_addr;
- if(debug_tensorcore){
+ if(core->get_gpu()->gpgpu_ctx->debug_tensorcore){
printf("wmma:store:thread%d=%x,%x,%x,%x,%x,%x,%x,%x\n",thrd,v[0].s64,v[1].s64,v[2].s64,v[3].s64,v[4].s64,v[5].s64,v[6].s64,v[7].s64);
float temp;
int l;
@@ -3175,7 +3178,7 @@ void mma_st_impl( const ptx_instruction *pI, core_t *core, warp_inst_t &inst )
mem_txn_addr[num_mem_txn++]=push_addr;
}
- if(debug_tensorcore)
+ if(core->get_gpu()->gpgpu_ctx->debug_tensorcore)
printf("wmma:store:thread%d=%x,%x,%x,%x,%x,%x,%x,%x\n",thrd,nw_v[0].s64,nw_v[1].s64,nw_v[2].s64,nw_v[3].s64,nw_v[4].s64,nw_v[5].s64,nw_v[6].s64,nw_v[7].s64);
}
}
@@ -3238,7 +3241,7 @@ void mma_ld_impl( const ptx_instruction *pI, core_t *core, warp_inst_t &inst )
type_info_key::type_decode(type,size,t);
ptx_reg_t data[16];
- if(debug_tensorcore)
+ if(core->get_gpu()->gpgpu_ctx->debug_tensorcore)
printf("mma_ld: thrd=%d,addr=%x, fpsize=%d, stride=%d\n",thrd,src1_data.u32,size,src2_data.u32);
addr_t new_addr = addr+thread_group_offset(thrd,wmma_type,wmma_layout,type,stride)*size/8;
@@ -3334,7 +3337,7 @@ void mma_ld_impl( const ptx_instruction *pI, core_t *core, warp_inst_t &inst )
inst.data_size = 4; // 4 byte transaction
assert( inst.memory_op == insn_memory_op );
- if(debug_tensorcore){
+ if(core->get_gpu()->gpgpu_ctx->debug_tensorcore){
if(type==F16_TYPE){
printf("\nmma_ld:thread%d= ",thrd);
for(i=0;i<16;i++){
@@ -3384,7 +3387,7 @@ void mma_ld_impl( const ptx_instruction *pI, core_t *core, warp_inst_t &inst )
thread->set_vector_operand_values(dst,nw_data[0],nw_data[1],nw_data[2],nw_data[3]);
else
thread->set_wmma_vector_operand_values(dst,nw_data[0],nw_data[1],nw_data[2],nw_data[3],nw_data[4],nw_data[5],nw_data[6],nw_data[7]);
- if(debug_tensorcore){
+ if(core->get_gpu()->gpgpu_ctx->debug_tensorcore){
printf("mma_ld:data[0].s64=%x,data[1].s64=%x,new_data[0].s64=%x\n",data[0].u64,data[1].u64,nw_data[0].u64);
printf("mma_ld:data[2].s64=%x,data[3].s64=%x,new_data[1].s64=%x\n",data[2].u64,data[3].u64,nw_data[1].u64);
printf("mma_ld:data[4].s64=%x,data[5].s64=%x,new_data[2].s64=%x\n",data[4].u64,data[5].u64,nw_data[2].u64);
@@ -5141,7 +5144,6 @@ void sured_impl( const ptx_instruction *pI, ptx_thread_info *thread ) { inst_not
void sust_impl( const ptx_instruction *pI, ptx_thread_info *thread ) { inst_not_implemented(pI); }
void suq_impl( const ptx_instruction *pI, ptx_thread_info *thread ) { inst_not_implemented(pI); }
-ptx_reg_t* ptx_tex_regs = NULL;
union intfloat {
int a;
@@ -5255,9 +5257,10 @@ void tex_impl( const ptx_instruction *pI, ptx_thread_info *thread )
unsigned c_type = pI->get_type2();
fflush(stdout);
ptx_reg_t data1, data2, data3, data4;
- if (!ptx_tex_regs) ptx_tex_regs = new ptx_reg_t[4];
+ if (!thread->get_gpu()->gpgpu_ctx->func_sim->ptx_tex_regs)
+ thread->get_gpu()->gpgpu_ctx->func_sim->ptx_tex_regs = new ptx_reg_t[4];
unsigned nelem = src2.get_vect_nelem();
- thread->get_vector_operand_values(src2, ptx_tex_regs, nelem); //ptx_reg should be 4 entry vector type...coordinates into texture
+ thread->get_vector_operand_values(src2, thread->get_gpu()->gpgpu_ctx->func_sim->ptx_tex_regs, nelem); //ptx_reg should be 4 entry vector type...coordinates into texture
/*
For programs with many streams, textures can be bound and unbound
asynchronously. This means we need to use the kernel's "snapshot" of
@@ -5294,7 +5297,7 @@ void tex_impl( const ptx_instruction *pI, ptx_thread_info *thread )
height = cuArray->height;
if (texref->normalized) {
assert(c_type == F32_TYPE);
- x_f32 = ptx_tex_regs[0].f32;
+ x_f32 = thread->get_gpu()->gpgpu_ctx->func_sim->ptx_tex_regs[0].f32;
if (texref->addressMode[0] == cudaAddressModeClamp) {
x_f32 = (x_f32 > 1.0)? 1.0 : x_f32;
x_f32 = (x_f32 < 0.0)? 0.0 : x_f32;
@@ -5317,11 +5320,11 @@ void tex_impl( const ptx_instruction *pI, ptx_thread_info *thread )
} else {
switch ( c_type ) {
case S32_TYPE:
- x = ptx_tex_regs[0].s32;
+ x = thread->get_gpu()->gpgpu_ctx->func_sim->ptx_tex_regs[0].s32;
assert(texref->filterMode == cudaFilterModePoint);
break;
case F32_TYPE:
- x_f32 = ptx_tex_regs[0].f32;
+ x_f32 = thread->get_gpu()->gpgpu_ctx->func_sim->ptx_tex_regs[0].f32;
alpha = x_f32 - floor(x_f32); // offset into subtexel (for linear sampling)
x = (int) x_f32;
break;
@@ -5344,8 +5347,8 @@ void tex_impl( const ptx_instruction *pI, ptx_thread_info *thread )
width = cuArray->width;
height = cuArray->height;
if (texref->normalized) {
- x_f32 = reduce_precision(ptx_tex_regs[0].f32,16);
- y_f32 = reduce_precision(ptx_tex_regs[1].f32,15);
+ x_f32 = reduce_precision(thread->get_gpu()->gpgpu_ctx->func_sim->ptx_tex_regs[0].f32,16);
+ y_f32 = reduce_precision(thread->get_gpu()->gpgpu_ctx->func_sim->ptx_tex_regs[1].f32,15);
if (texref->addressMode[0]) {//clamp
if (x_f32<0) x_f32 = 0;
@@ -5375,8 +5378,8 @@ void tex_impl( const ptx_instruction *pI, ptx_thread_info *thread )
y = (int) floor(y_f32 * height);
}
} else {
- x_f32 = ptx_tex_regs[0].f32;
- y_f32 = ptx_tex_regs[1].f32;
+ x_f32 = thread->get_gpu()->gpgpu_ctx->func_sim->ptx_tex_regs[0].f32;
+ y_f32 = thread->get_gpu()->gpgpu_ctx->func_sim->ptx_tex_regs[1].f32;
alpha = x_f32 - floor(x_f32);
beta = y_f32 - floor(y_f32);
diff --git a/src/cuda-sim/memory.cc b/src/cuda-sim/memory.cc
index 9554f55..4b2acdf 100644
--- a/src/cuda-sim/memory.cc
+++ b/src/cuda-sim/memory.cc
@@ -28,6 +28,7 @@
#include "memory.h"
#include <stdlib.h>
#include "../debug.h"
+#include "../../libcuda/gpgpu_context.h"
template<unsigned BSIZE> memory_space_impl<BSIZE>::memory_space_impl( std::string name, unsigned hash_size )
{
@@ -88,7 +89,7 @@ template<unsigned BSIZE> void memory_space_impl<BSIZE>::write( mem_addr_t addr,
for( i=m_watchpoints.begin(); i!=m_watchpoints.end(); i++ ) {
mem_addr_t wa = i->second;
if( ((addr<=wa) && ((addr+length)>wa)) || ((addr>wa) && (addr < (wa+4))) )
- hit_watchpoint(i->first,thd,pI);
+ thd->get_gpu()->gpgpu_ctx->the_gpgpusim->g_the_gpu->hit_watchpoint(i->first,thd,pI);
}
}
}
diff --git a/src/cuda-sim/ptx-stats.cc b/src/cuda-sim/ptx-stats.cc
index 0a9f08d..22517df 100644
--- a/src/cuda-sim/ptx-stats.cc
+++ b/src/cuda-sim/ptx-stats.cc
@@ -32,12 +32,9 @@
#include <stdio.h>
#include <map>
#include "../tr1_hash_map.h"
+#include "../../libcuda/gpgpu_context.h"
-// options
-bool enable_ptx_file_line_stats;
-char * ptx_line_stats_filename = NULL;
-
-void ptx_file_line_stats_options(option_parser_t opp)
+void ptx_stats::ptx_file_line_stats_options(option_parser_t opp)
{
option_parser_register(opp, "-enable_ptx_file_line_stats", OPT_BOOL,
&enable_ptx_file_line_stats,
@@ -118,7 +115,7 @@ typedef tr1_hash_map<ptx_file_line, ptx_file_line_stats, hash_ptx_file_line> ptx
static ptx_file_line_stats_map_t ptx_file_line_stats_tracker;
// output statistics to a file
-void ptx_file_line_stats_write_file()
+void ptx_stats::ptx_file_line_stats_write_file()
{
// check if stat collection is turned on
if (enable_ptx_file_line_stats == 0) return;
@@ -154,27 +151,27 @@ void ptx_file_line_stats_add_exec_count(const ptx_instruction *pInsn)
// attribute pipeline latency to this ptx instruction (specified by the pc)
// pipeline latency is the number of cycles a warp with this instruction spent in the pipeline
-void ptx_file_line_stats_add_latency(unsigned pc, unsigned latency)
+void ptx_stats::ptx_file_line_stats_add_latency(unsigned pc, unsigned latency)
{
- const ptx_instruction *pInsn = function_info::pc_to_instruction(pc);
+ const ptx_instruction *pInsn = gpgpu_ctx->pc_to_instruction(pc);
ptx_file_line_stats_tracker[ptx_file_line(pInsn->source_file(), pInsn->source_line())].latency += latency;
}
// attribute dram traffic to this ptx instruction (specified by the pc)
// dram traffic is counted in number of requests
-void ptx_file_line_stats_add_dram_traffic(unsigned pc, unsigned dram_traffic)
+void ptx_stats::ptx_file_line_stats_add_dram_traffic(unsigned pc, unsigned dram_traffic)
{
- const ptx_instruction *pInsn = function_info::pc_to_instruction(pc);
+ const ptx_instruction *pInsn = gpgpu_ctx->pc_to_instruction(pc);
ptx_file_line_stats_tracker[ptx_file_line(pInsn->source_file(), pInsn->source_line())].dram_traffic += dram_traffic;
}
// attribute the number of shared memory access cycles to a ptx instruction
// counts both the number of warps doing shared memory access and the number of cycles involved
-void ptx_file_line_stats_add_smem_bank_conflict(unsigned pc, unsigned n_way_bkconflict)
+void ptx_stats::ptx_file_line_stats_add_smem_bank_conflict(unsigned pc, unsigned n_way_bkconflict)
{
- const ptx_instruction *pInsn = function_info::pc_to_instruction(pc);
+ const ptx_instruction *pInsn = gpgpu_ctx->pc_to_instruction(pc);
ptx_file_line_stats& line_stats = ptx_file_line_stats_tracker[ptx_file_line(pInsn->source_file(), pInsn->source_line())];
line_stats.smem_n_way_bank_conflict_total += n_way_bkconflict;
@@ -183,9 +180,9 @@ void ptx_file_line_stats_add_smem_bank_conflict(unsigned pc, unsigned n_way_bkco
// attribute a non-coalesced mem access to a ptx instruction
// counts both the number of warps causing this and the number of memory requests generated
-void ptx_file_line_stats_add_uncoalesced_gmem(unsigned pc, unsigned n_access)
+void ptx_stats::ptx_file_line_stats_add_uncoalesced_gmem(unsigned pc, unsigned n_access)
{
- const ptx_instruction *pInsn = function_info::pc_to_instruction(pc);
+ const ptx_instruction *pInsn = gpgpu_ctx->pc_to_instruction(pc);
ptx_file_line_stats& line_stats = ptx_file_line_stats_tracker[ptx_file_line(pInsn->source_file(), pInsn->source_line())];
line_stats.gmem_n_access_total += n_access;
@@ -242,17 +239,17 @@ void ptx_file_line_stats_create_exposed_latency_tracker(int n_shader_cores)
}
// add an inflight memory instruction
-void ptx_file_line_stats_add_inflight_memory_insn(int sc_id, unsigned pc)
+void ptx_stats::ptx_file_line_stats_add_inflight_memory_insn(int sc_id, unsigned pc)
{
- const ptx_instruction *pInsn = function_info::pc_to_instruction(pc);
+ const ptx_instruction *pInsn = gpgpu_ctx->pc_to_instruction(pc);
inflight_mem_tracker[sc_id].add_count(pInsn);
}
// remove an inflight memory instruction
-void ptx_file_line_stats_sub_inflight_memory_insn(int sc_id, unsigned pc)
+void ptx_stats::ptx_file_line_stats_sub_inflight_memory_insn(int sc_id, unsigned pc)
{
- const ptx_instruction *pInsn = function_info::pc_to_instruction(pc);
+ const ptx_instruction *pInsn = gpgpu_ctx->pc_to_instruction(pc);
inflight_mem_tracker[sc_id].sub_count(pInsn);
}
@@ -265,9 +262,9 @@ void ptx_file_line_stats_commit_exposed_latency(int sc_id, int exposed_latency)
}
// attribute the number of warp divergence to a ptx instruction
-void ptx_file_line_stats_add_warp_divergence(unsigned pc, unsigned n_way_divergence)
+void ptx_stats::ptx_file_line_stats_add_warp_divergence(unsigned pc, unsigned n_way_divergence)
{
- const ptx_instruction *pInsn = function_info::pc_to_instruction(pc);
+ const ptx_instruction *pInsn = gpgpu_ctx->pc_to_instruction(pc);
ptx_file_line_stats& line_stats = ptx_file_line_stats_tracker[ptx_file_line(pInsn->source_file(), pInsn->source_line())];
line_stats.warp_divergence += n_way_divergence;
diff --git a/src/cuda-sim/ptx-stats.h b/src/cuda-sim/ptx-stats.h
index 4fc6599..246b4ce 100644
--- a/src/cuda-sim/ptx-stats.h
+++ b/src/cuda-sim/ptx-stats.h
@@ -29,13 +29,6 @@
#include "../option_parser.h"
-extern bool enable_ptx_file_line_stats;
-
-// set options
-void ptx_file_line_stats_options(option_parser_t opp);
-
-// output stats to a file
-void ptx_file_line_stats_write_file();
#ifdef __cplusplus
// stat collection interface to cuda-sim
@@ -44,15 +37,32 @@ void ptx_file_line_stats_add_exec_count(const ptx_instruction *pInsn);
#endif
// stat collection interface to gpgpu-sim
-void ptx_file_line_stats_add_latency(unsigned pc, unsigned latency);
-void ptx_file_line_stats_add_dram_traffic(unsigned pc, unsigned dram_traffic);
-void ptx_file_line_stats_add_smem_bank_conflict(unsigned pc, unsigned n_way_bkconflict);
-void ptx_file_line_stats_add_uncoalesced_gmem(unsigned pc, unsigned n_access);
void ptx_file_line_stats_create_exposed_latency_tracker(int n_shader_cores);
-void ptx_file_line_stats_add_inflight_memory_insn(int sc_id, unsigned pc);
-void ptx_file_line_stats_sub_inflight_memory_insn(int sc_id, unsigned pc);
void ptx_file_line_stats_commit_exposed_latency(int sc_id, int exposed_latency);
-void ptx_file_line_stats_add_warp_divergence(unsigned pc, unsigned n_way_divergence);
+class gpgpu_context;
+class ptx_stats {
+ public:
+ ptx_stats(gpgpu_context* ctx) {
+ ptx_line_stats_filename = NULL;
+ gpgpu_ctx = ctx;
+ }
+ char * ptx_line_stats_filename;
+ bool enable_ptx_file_line_stats;
+ gpgpu_context* gpgpu_ctx;
+ // set options
+ void ptx_file_line_stats_options(option_parser_t opp);
+
+ // output stats to a file
+ void ptx_file_line_stats_write_file();
+ // stat collection interface to gpgpu-sim
+ void ptx_file_line_stats_add_latency(unsigned pc, unsigned latency);
+ void ptx_file_line_stats_add_dram_traffic(unsigned pc, unsigned dram_traffic);
+ void ptx_file_line_stats_add_smem_bank_conflict(unsigned pc, unsigned n_way_bkconflict);
+ void ptx_file_line_stats_add_uncoalesced_gmem(unsigned pc, unsigned n_access);
+ void ptx_file_line_stats_add_inflight_memory_insn(int sc_id, unsigned pc);
+ void ptx_file_line_stats_sub_inflight_memory_insn(int sc_id, unsigned pc);
+ void ptx_file_line_stats_add_warp_divergence(unsigned pc, unsigned n_way_divergence);
+};
diff --git a/src/cuda-sim/ptx.l b/src/cuda-sim/ptx.l
index 36a8a4d..2dadda4 100644
--- a/src/cuda-sim/ptx.l
+++ b/src/cuda-sim/ptx.l
@@ -31,21 +31,27 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
%option noyywrap
%option yylineno
%option prefix="ptx_"
+
+%option bison-bridge
+%option reentrant
+
%{
#include "opcodes.h"
+#include "ptx_parser.h"
#include "ptx.tab.h"
#include <string.h>
+#include "../../libcuda/gpgpu_context.h"
-#define LINEBUF_SIZE (64*1024)
-char linebuf[LINEBUF_SIZE];
-unsigned col = 0;
-#define TC col+=strlen(ptx_text);
+#define LINEBUF_SIZE (4*1024)
+#define TC recognizer->col+=strlen(yytext);
#define CHECK_UNSIGNED \
if( yytext[strlen(yytext)-1]=='U' ) { \
printf("GPGPU-Sim: ERROR ** U modifier not implemented\n"); \
abort(); \
}
-int ptx_error( const char *s );
+#define YY_DECL int ptx_lex \
+ (YYSTYPE * yylval_param , yyscan_t yyscanner, ptx_recognizer* recognizer)
+int ptx_error( yyscan_t yyscanner, ptx_recognizer* recognizer, const char *s );
%}
%s IN_STRING
@@ -54,123 +60,124 @@ int ptx_error( const char *s );
%x NOT_OPCODE
%%
-abs TC; ptx_lval.int_value = ABS_OP; return OPCODE;
-add TC; ptx_lval.int_value = ADD_OP; return OPCODE;
-addp TC; ptx_lval.int_value = ADDP_OP; return OPCODE;
-addc TC; ptx_lval.int_value = ADDC_OP; return OPCODE;
-and TC; ptx_lval.int_value = AND_OP; return OPCODE;
-andn TC; ptx_lval.int_value = ANDN_OP; return OPCODE;
-atom TC; ptx_lval.int_value = ATOM_OP; return OPCODE;
-bar.warp TC; ptx_lval.int_value = NOP_OP; return OPCODE;
-bar TC; ptx_lval.int_value = BAR_OP; return OPCODE;
-bfe TC; ptx_lval.int_value = BFE_OP; return OPCODE;
-bfi TC; ptx_lval.int_value = BFI_OP; return OPCODE;
-bfind TC; ptx_lval.int_value = BFIND_OP; return OPCODE;
-bra TC; ptx_lval.int_value = BRA_OP; return OPCODE;
-brx TC; ptx_lval.int_value = BRX_OP; return OPCODE;
-brev TC; ptx_lval.int_value = BREV_OP; return OPCODE;
-brkpt TC; ptx_lval.int_value = BRKPT_OP; return OPCODE;
+abs TC; yylval->int_value = ABS_OP; return OPCODE;
+add TC; yylval->int_value = ADD_OP; return OPCODE;
+addp TC; yylval->int_value = ADDP_OP; return OPCODE;
+addc TC; yylval->int_value = ADDC_OP; return OPCODE;
+and TC; yylval->int_value = AND_OP; return OPCODE;
+andn TC; yylval->int_value = ANDN_OP; return OPCODE;
+atom TC; yylval->int_value = ATOM_OP; return OPCODE;
+bar.warp TC; yylval->int_value = NOP_OP; return OPCODE;
+bar TC; yylval->int_value = BAR_OP; return OPCODE;
+bfe TC; yylval->int_value = BFE_OP; return OPCODE;
+bfi TC; yylval->int_value = BFI_OP; return OPCODE;
+bfind TC; yylval->int_value = BFIND_OP; return OPCODE;
+bra TC; yylval->int_value = BRA_OP; return OPCODE;
+brx TC; yylval->int_value = BRX_OP; return OPCODE;
+brev TC; yylval->int_value = BREV_OP; return OPCODE;
+brkpt TC; yylval->int_value = BRKPT_OP; return OPCODE;
-wmma TC; ptx_lval.int_value = MMA_OP; return OPCODE;
-wmma\.load TC; ptx_lval.int_value = MMA_LD_OP; return OPCODE;
-wmma\.store TC; ptx_lval.int_value = MMA_ST_OP; return OPCODE;
+wmma TC; yylval->int_value = MMA_OP; return OPCODE;
+wmma\.load TC; yylval->int_value = MMA_LD_OP; return OPCODE;
+wmma\.store TC; yylval->int_value = MMA_ST_OP; return OPCODE;
-call TC; BEGIN(NOT_OPCODE); ptx_lval.int_value = CALL_OP; return OPCODE; // blocking opcode token in case the callee has the same name as an opcode
-callp TC; BEGIN(NOT_OPCODE); ptx_lval.int_value = CALLP_OP; return OPCODE;
-clz TC; ptx_lval.int_value = CLZ_OP; return OPCODE;
-cnot TC; ptx_lval.int_value = CNOT_OP; return OPCODE;
-cos TC; ptx_lval.int_value = COS_OP; return OPCODE;
-cvt TC; ptx_lval.int_value = CVT_OP; return OPCODE;
-cvta TC; ptx_lval.int_value = CVTA_OP; return OPCODE;
-div TC; ptx_lval.int_value = DIV_OP; return OPCODE;
-dp4a TC; ptx_lval.int_value = DP4A_OP; return OPCODE;
-ex2 TC; ptx_lval.int_value = EX2_OP; return OPCODE;
-exit TC; ptx_lval.int_value = EXIT_OP; return OPCODE;
-fma TC; ptx_lval.int_value = FMA_OP; return OPCODE;
-isspacep TC; ptx_lval.int_value = ISSPACEP_OP; return OPCODE;
-ld TC; ptx_lval.int_value = LD_OP; return OPCODE;
-ld.volatile TC; ptx_lval.int_value = LD_OP; return OPCODE;
-ldu TC; ptx_lval.int_value = LDU_OP; return OPCODE;
-lg2 TC; ptx_lval.int_value = LG2_OP; return OPCODE;
-mad24 TC; ptx_lval.int_value = MAD24_OP; return OPCODE;
-mad TC; ptx_lval.int_value = MAD_OP; return OPCODE;
-madc TC; ptx_lval.int_value = MADC_OP; return OPCODE;
-madp TC; ptx_lval.int_value = MADP_OP; return OPCODE;
-max TC; ptx_lval.int_value = MAX_OP; return OPCODE;
-membar TC; ptx_lval.int_value = MEMBAR_OP; return OPCODE;
-min TC; ptx_lval.int_value = MIN_OP; return OPCODE;
-mov TC; ptx_lval.int_value = MOV_OP; return OPCODE;
-mul24 TC; ptx_lval.int_value = MUL24_OP; return OPCODE;
-mul TC; ptx_lval.int_value = MUL_OP; return OPCODE;
-neg TC; ptx_lval.int_value = NEG_OP; return OPCODE;
-nandn TC; ptx_lval.int_value = NANDN_OP; return OPCODE;
-norn TC; ptx_lval.int_value = NORN_OP; return OPCODE;
-not TC; ptx_lval.int_value = NOT_OP; return OPCODE;
-or TC; ptx_lval.int_value = OR_OP; return OPCODE;
-orn TC; ptx_lval.int_value = ORN_OP; return OPCODE;
-pmevent TC; ptx_lval.int_value = PMEVENT_OP; return OPCODE;
-popc TC; ptx_lval.int_value = POPC_OP; return OPCODE;
-prefetch TC; ptx_lval.int_value = PREFETCH_OP; return OPCODE;
-prefetchu TC; ptx_lval.int_value = PREFETCHU_OP; return OPCODE;
-prmt TC; ptx_lval.int_value = PRMT_OP; return OPCODE;
-rcp TC; ptx_lval.int_value = RCP_OP; return OPCODE;
-red TC; ptx_lval.int_value = RED_OP; return OPCODE;
-rem TC; ptx_lval.int_value = REM_OP; return OPCODE;
-ret TC; ptx_lval.int_value = RET_OP; return OPCODE;
-retp TC; ptx_lval.int_value = RETP_OP; return OPCODE;
-rsqrt TC; ptx_lval.int_value = RSQRT_OP; return OPCODE;
-sad TC; ptx_lval.int_value = SAD_OP; return OPCODE;
-selp TC; ptx_lval.int_value = SELP_OP; return OPCODE;
-setp TC; ptx_lval.int_value = SETP_OP; return OPCODE;
-set TC; ptx_lval.int_value = SET_OP; return OPCODE;
-shfl TC; ptx_lval.int_value = SHFL_OP; return OPCODE;
-shl TC; ptx_lval.int_value = SHL_OP; return OPCODE;
-shr TC; ptx_lval.int_value = SHR_OP; return OPCODE;
-sin TC; ptx_lval.int_value = SIN_OP; return OPCODE;
-slct TC; ptx_lval.int_value = SLCT_OP; return OPCODE;
-sqrt TC; ptx_lval.int_value = SQRT_OP; return OPCODE;
-sst TC; ptx_lval.int_value = SST_OP; return OPCODE;
-ssy TC; ptx_lval.int_value = SSY_OP; return OPCODE;
-st TC; ptx_lval.int_value = ST_OP; return OPCODE;
-st.volatile TC; ptx_lval.int_value = ST_OP; return OPCODE;
-sub TC; ptx_lval.int_value = SUB_OP; return OPCODE;
-subc TC; ptx_lval.int_value = SUBC_OP; return OPCODE;
-suld TC; ptx_lval.int_value = SULD_OP; return OPCODE;
-sured TC; ptx_lval.int_value = SURED_OP; return OPCODE;
-surst TC; ptx_lval.int_value = SUST_OP; return OPCODE;
-suq TC; ptx_lval.int_value = SUQ_OP; return OPCODE;
-tex TC; BEGIN(NOT_OPCODE); ptx_lval.int_value = TEX_OP; return OPCODE;
-txq TC; ptx_lval.int_value = TEX_OP; return OPCODE;
-trap TC; ptx_lval.int_value = TRAP_OP; return OPCODE;
-vabsdiff TC; ptx_lval.int_value = VABSDIFF_OP; return OPCODE;
-vadd TC; ptx_lval.int_value = VADD_OP; return OPCODE;
-vmad TC; ptx_lval.int_value = VMAD_OP; return OPCODE;
-vmax TC; ptx_lval.int_value = VMAX_OP; return OPCODE;
-vmin TC; ptx_lval.int_value = VMIN_OP; return OPCODE;
-vset TC; ptx_lval.int_value = VSET_OP; return OPCODE;
-vshl TC; ptx_lval.int_value = VSHL_OP; return OPCODE;
-vshr TC; ptx_lval.int_value = VSHR_OP; return OPCODE;
-vsub TC; ptx_lval.int_value = VSUB_OP; return OPCODE;
-vote TC; ptx_lval.int_value = VOTE_OP; return OPCODE;
-xor TC; ptx_lval.int_value = XOR_OP; return OPCODE;
-nop TC; ptx_lval.int_value = NOP_OP; return OPCODE;
-break TC; ptx_lval.int_value = BREAK_OP; return OPCODE;
-breakaddr TC; ptx_lval.int_value = BREAKADDR_OP; return OPCODE;
+call TC; BEGIN(NOT_OPCODE); yylval->int_value = CALL_OP; return OPCODE; // blocking opcode token in case the callee has the same name as an opcode
+callp TC; BEGIN(NOT_OPCODE); yylval->int_value = CALLP_OP; return OPCODE;
+clz TC; yylval->int_value = CLZ_OP; return OPCODE;
+cnot TC; yylval->int_value = CNOT_OP; return OPCODE;
+cos TC; yylval->int_value = COS_OP; return OPCODE;
+cvt TC; yylval->int_value = CVT_OP; return OPCODE;
+cvta TC; yylval->int_value = CVTA_OP; return OPCODE;
+div TC; yylval->int_value = DIV_OP; return OPCODE;
+dp4a TC; yylval->int_value = DP4A_OP; return OPCODE;
+ex2 TC; yylval->int_value = EX2_OP; return OPCODE;
+exit TC; yylval->int_value = EXIT_OP; return OPCODE;
+fma TC; yylval->int_value = FMA_OP; return OPCODE;
+isspacep TC; yylval->int_value = ISSPACEP_OP; return OPCODE;
+ld TC; yylval->int_value = LD_OP; return OPCODE;
+ld.volatile TC; yylval->int_value = LD_OP; return OPCODE;
+ldu TC; yylval->int_value = LDU_OP; return OPCODE;
+lg2 TC; yylval->int_value = LG2_OP; return OPCODE;
+mad24 TC; yylval->int_value = MAD24_OP; return OPCODE;
+mad TC; yylval->int_value = MAD_OP; return OPCODE;
+madc TC; yylval->int_value = MADC_OP; return OPCODE;
+madp TC; yylval->int_value = MADP_OP; return OPCODE;
+max TC; yylval->int_value = MAX_OP; return OPCODE;
+membar TC; yylval->int_value = MEMBAR_OP; return OPCODE;
+min TC; yylval->int_value = MIN_OP; return OPCODE;
+mov TC; yylval->int_value = MOV_OP; return OPCODE;
+mul24 TC; yylval->int_value = MUL24_OP; return OPCODE;
+mul TC; yylval->int_value = MUL_OP; return OPCODE;
+neg TC; yylval->int_value = NEG_OP; return OPCODE;
+nandn TC; yylval->int_value = NANDN_OP; return OPCODE;
+norn TC; yylval->int_value = NORN_OP; return OPCODE;
+not TC; yylval->int_value = NOT_OP; return OPCODE;
+or TC; yylval->int_value = OR_OP; return OPCODE;
+orn TC; yylval->int_value = ORN_OP; return OPCODE;
+pmevent TC; yylval->int_value = PMEVENT_OP; return OPCODE;
+popc TC; yylval->int_value = POPC_OP; return OPCODE;
+prefetch TC; yylval->int_value = PREFETCH_OP; return OPCODE;
+prefetchu TC; yylval->int_value = PREFETCHU_OP; return OPCODE;
+prmt TC; yylval->int_value = PRMT_OP; return OPCODE;
+rcp TC; yylval->int_value = RCP_OP; return OPCODE;
+red TC; yylval->int_value = RED_OP; return OPCODE;
+rem TC; yylval->int_value = REM_OP; return OPCODE;
+ret TC; yylval->int_value = RET_OP; return OPCODE;
+retp TC; yylval->int_value = RETP_OP; return OPCODE;
+rsqrt TC; yylval->int_value = RSQRT_OP; return OPCODE;
+sad TC; yylval->int_value = SAD_OP; return OPCODE;
+selp TC; yylval->int_value = SELP_OP; return OPCODE;
+setp TC; yylval->int_value = SETP_OP; return OPCODE;
+set TC; yylval->int_value = SET_OP; return OPCODE;
+shfl TC; yylval->int_value = SHFL_OP; return OPCODE;
+shl TC; yylval->int_value = SHL_OP; return OPCODE;
+shr TC; yylval->int_value = SHR_OP; return OPCODE;
+sin TC; yylval->int_value = SIN_OP; return OPCODE;
+slct TC; yylval->int_value = SLCT_OP; return OPCODE;
+sqrt TC; yylval->int_value = SQRT_OP; return OPCODE;
+sst TC; yylval->int_value = SST_OP; return OPCODE;
+ssy TC; yylval->int_value = SSY_OP; return OPCODE;
+st TC; yylval->int_value = ST_OP; return OPCODE;
+st.volatile TC; yylval->int_value = ST_OP; return OPCODE;
+sub TC; yylval->int_value = SUB_OP; return OPCODE;
+subc TC; yylval->int_value = SUBC_OP; return OPCODE;
+suld TC; yylval->int_value = SULD_OP; return OPCODE;
+sured TC; yylval->int_value = SURED_OP; return OPCODE;
+surst TC; yylval->int_value = SUST_OP; return OPCODE;
+suq TC; yylval->int_value = SUQ_OP; return OPCODE;
+tex TC; BEGIN(NOT_OPCODE); yylval->int_value = TEX_OP; return OPCODE;
+txq TC; yylval->int_value = TEX_OP; return OPCODE;
+trap TC; yylval->int_value = TRAP_OP; return OPCODE;
+vabsdiff TC; yylval->int_value = VABSDIFF_OP; return OPCODE;
+vadd TC; yylval->int_value = VADD_OP; return OPCODE;
+vmad TC; yylval->int_value = VMAD_OP; return OPCODE;
+vmax TC; yylval->int_value = VMAX_OP; return OPCODE;
+vmin TC; yylval->int_value = VMIN_OP; return OPCODE;
+vset TC; yylval->int_value = VSET_OP; return OPCODE;
+vshl TC; yylval->int_value = VSHL_OP; return OPCODE;
+vshr TC; yylval->int_value = VSHR_OP; return OPCODE;
+vsub TC; yylval->int_value = VSUB_OP; return OPCODE;
+vote TC; yylval->int_value = VOTE_OP; return OPCODE;
+xor TC; yylval->int_value = XOR_OP; return OPCODE;
+nop TC; yylval->int_value = NOP_OP; return OPCODE;
+break TC; yylval->int_value = BREAK_OP; return OPCODE;
+breakaddr TC; yylval->int_value = BREAKADDR_OP; return OPCODE;
"CPTX_END" printf("ENDING CUSTOM PTX.\n"); BEGIN(IN_COMMENT);
<INITIAL,NOT_OPCODE,IN_INST,IN_FUNC_DECL>{
-\.a\.sync TC; ptx_lval.int_value = LOAD_A; return WMMA_DIRECTIVE;
-\.b\.sync TC; ptx_lval.int_value = LOAD_B; return WMMA_DIRECTIVE;
-\.c\.sync TC; ptx_lval.int_value = LOAD_C; return WMMA_DIRECTIVE;
-\.d\.sync TC; ptx_lval.int_value = STORE_D; return WMMA_DIRECTIVE;
-\.mma\.sync TC;ptx_lval.int_value=MMA; return WMMA_DIRECTIVE;
+\.a\.sync TC; yylval->int_value = LOAD_A; return WMMA_DIRECTIVE;
+\.b\.sync TC; yylval->int_value = LOAD_B; return WMMA_DIRECTIVE;
+\.c\.sync TC; yylval->int_value = LOAD_C; return WMMA_DIRECTIVE;
+\.d\.sync TC; yylval->int_value = STORE_D; return WMMA_DIRECTIVE;
+\.mma\.sync TC;yylval->int_value=MMA; return WMMA_DIRECTIVE;
+
+\.row TC; yylval->int_value = ROW; return LAYOUT;
+\.col TC; yylval->int_value = COL; return LAYOUT;
+\.m16n16k16 TC; yylval->int_value = M16N16K16; return CONFIGURATION;
+\.m32n8k16 TC; yylval->int_value = M32N8K16; return CONFIGURATION;
+\.m8n32k16 TC; yylval->int_value = M8N32K16; return CONFIGURATION;
-\.row TC; ptx_lval.int_value = ROW; return LAYOUT;
-\.col TC; ptx_lval.int_value = COL; return LAYOUT;
-\.m16n16k16 TC; ptx_lval.int_value = M16N16K16; return CONFIGURATION;
-\.m32n8k16 TC; ptx_lval.int_value = M32N8K16; return CONFIGURATION;
-\.m8n32k16 TC; ptx_lval.int_value = M8N32K16; return CONFIGURATION;
\.f4e TC; return PRMT_F4E_MODE;
\.b4e TC; return PRMT_B4E_MODE;
\.rc8 TC; return PRMT_RC8_MODE;
@@ -183,8 +190,8 @@ breakaddr TC; ptx_lval.int_value = BREAKADDR_OP; return OPCODE;
\.byte TC; return BYTE_DIRECTIVE; /* not in PTX 2.1 */
\.callprototype TC; return CALLPROTOTYPE_DIRECTIVE;
\.calltargets TC; return CALLTARGETS_DIRECTIVE;
-\.const\[[0-9]+\] TC; ptx_lval.int_value = atoi(yytext+7); return CONST_DIRECTIVE;
-\.const TC; ptx_lval.int_value = 0; return CONST_DIRECTIVE;
+\.const\[[0-9]+\] TC; yylval->int_value = atoi(yytext+7); return CONST_DIRECTIVE;
+\.const TC; yylval->int_value = 0; return CONST_DIRECTIVE;
\.entry TC; return ENTRY_DIRECTIVE;
\.extern TC; return EXTERN_DIRECTIVE;
\.file TC; BEGIN(INITIAL); return FILE_DIRECTIVE;
@@ -219,40 +226,40 @@ breakaddr TC; ptx_lval.int_value = BREAKADDR_OP; return OPCODE;
\.constptr TC; return CONSTPTR_DIRECTIVE; /* Ptx plus directive for pointer to constant memory */
\.ptr TC; return PTR_DIRECTIVE; /* Added for new OpenCL genrated code */
-"%clock" TC; ptx_lval.int_value = CLOCK_REG; return SPECIAL_REGISTER;
-"%halfclock" TC; ptx_lval.int_value = HALFCLOCK_ID; return SPECIAL_REGISTER;
-"%clock64" TC; ptx_lval.int_value = CLOCK64_REG; return SPECIAL_REGISTER;
-"%ctaid" TC; ptx_lval.int_value = CTAID_REG; return SPECIAL_REGISTER;
-"%envreg"[0-9]+ TC; sscanf(yytext+7,"%u",&ptx_lval.int_value); ptx_lval.int_value<<=16; ptx_lval.int_value += ENVREG_REG; return SPECIAL_REGISTER;
-"%gridid" TC; ptx_lval.int_value = GRIDID_REG; return SPECIAL_REGISTER;
-"%laneid" TC; ptx_lval.int_value = LANEID_REG; return SPECIAL_REGISTER;
-"%lanemask_eq" TC; ptx_lval.int_value = LANEMASK_EQ_REG; return SPECIAL_REGISTER;
-"%lanemask_le" TC; ptx_lval.int_value = LANEMASK_LE_REG; return SPECIAL_REGISTER;
-"%lanemask_lt" TC; ptx_lval.int_value = LANEMASK_LT_REG; return SPECIAL_REGISTER;
-"%lanemask_ge" TC; ptx_lval.int_value = LANEMASK_GE_REG; return SPECIAL_REGISTER;
-"%lanemask_gt" TC; ptx_lval.int_value = LANEMASK_GT_REG; return SPECIAL_REGISTER;
-"%nctaid" TC; ptx_lval.int_value = NCTAID_REG; return SPECIAL_REGISTER;
-"%ntid" TC; ptx_lval.int_value = NTID_REG; return SPECIAL_REGISTER;
-"%nsmid" TC; ptx_lval.int_value = NSMID_REG; return SPECIAL_REGISTER;
-"%nwarpid" TC; ptx_lval.int_value = NWARPID_REG; return SPECIAL_REGISTER;
-"%pm"[0-3] TC; sscanf(yytext+3,"%u",&ptx_lval.int_value); ptx_lval.int_value<<=16; ptx_lval.int_value += PM_REG; return SPECIAL_REGISTER;
-"%smid" TC; ptx_lval.int_value = SMID_REG; return SPECIAL_REGISTER;
-"%tid" TC; ptx_lval.int_value = TID_REG; return SPECIAL_REGISTER;
-"%warpid" TC; ptx_lval.int_value = WARPID_REG; return SPECIAL_REGISTER;
-"WARP_SZ" TC; ptx_lval.int_value = WARPSZ_REG; return SPECIAL_REGISTER;
+"%clock" TC; yylval->int_value = CLOCK_REG; return SPECIAL_REGISTER;
+"%halfclock" TC; yylval->int_value = HALFCLOCK_ID; return SPECIAL_REGISTER;
+"%clock64" TC; yylval->int_value = CLOCK64_REG; return SPECIAL_REGISTER;
+"%ctaid" TC; yylval->int_value = CTAID_REG; return SPECIAL_REGISTER;
+"%envreg"[0-9]+ TC; sscanf(yytext+7,"%u",&yylval->int_value); yylval->int_value<<=16; yylval->int_value += ENVREG_REG; return SPECIAL_REGISTER;
+"%gridid" TC; yylval->int_value = GRIDID_REG; return SPECIAL_REGISTER;
+"%laneid" TC; yylval->int_value = LANEID_REG; return SPECIAL_REGISTER;
+"%lanemask_eq" TC; yylval->int_value = LANEMASK_EQ_REG; return SPECIAL_REGISTER;
+"%lanemask_le" TC; yylval->int_value = LANEMASK_LE_REG; return SPECIAL_REGISTER;
+"%lanemask_lt" TC; yylval->int_value = LANEMASK_LT_REG; return SPECIAL_REGISTER;
+"%lanemask_ge" TC; yylval->int_value = LANEMASK_GE_REG; return SPECIAL_REGISTER;
+"%lanemask_gt" TC; yylval->int_value = LANEMASK_GT_REG; return SPECIAL_REGISTER;
+"%nctaid" TC; yylval->int_value = NCTAID_REG; return SPECIAL_REGISTER;
+"%ntid" TC; yylval->int_value = NTID_REG; return SPECIAL_REGISTER;
+"%nsmid" TC; yylval->int_value = NSMID_REG; return SPECIAL_REGISTER;
+"%nwarpid" TC; yylval->int_value = NWARPID_REG; return SPECIAL_REGISTER;
+"%pm"[0-3] TC; sscanf(yytext+3,"%u",&yylval->int_value); yylval->int_value<<=16; yylval->int_value += PM_REG; return SPECIAL_REGISTER;
+"%smid" TC; yylval->int_value = SMID_REG; return SPECIAL_REGISTER;
+"%tid" TC; yylval->int_value = TID_REG; return SPECIAL_REGISTER;
+"%warpid" TC; yylval->int_value = WARPID_REG; return SPECIAL_REGISTER;
+"WARP_SZ" TC; yylval->int_value = WARPSZ_REG; return SPECIAL_REGISTER;
-[a-zA-Z_][a-zA-Z0-9_$]* TC; ptx_lval.string_value = strdup(yytext); return IDENTIFIER;
-[$%][a-zA-Z0-9_$]+ TC; ptx_lval.string_value = strdup(yytext); return IDENTIFIER;
+[a-zA-Z_][a-zA-Z0-9_$]* TC; yylval->string_value = strdup(yytext); return IDENTIFIER;
+[$%][a-zA-Z0-9_$]+ TC; yylval->string_value = strdup(yytext); return IDENTIFIER;
-[0-9]+\.[0-9]+ TC; sscanf(yytext,"%lf", &ptx_lval.double_value); return DOUBLE_OPERAND;
+[0-9]+\.[0-9]+ TC; sscanf(yytext,"%lf", &yylval->double_value); return DOUBLE_OPERAND;
-0[xX][0-9a-fA-F]+U? TC; CHECK_UNSIGNED; sscanf(yytext,"%x", &ptx_lval.int_value); return INT_OPERAND;
+0[xX][0-9a-fA-F]+U? TC; CHECK_UNSIGNED; sscanf(yytext,"%x", &yylval->int_value); return INT_OPERAND;
0[0-7]+U? TC; printf("GPGPU-Sim: ERROR ** parsing octal not (yet) implemented\n"); abort(); return INT_OPERAND;
0[bB][01]+U? TC; printf("GPGPU-Sim: ERROR ** parsing binary not (yet) implemented\n"); abort(); return INT_OPERAND;
-[-]?[0-9]+U? TC; CHECK_UNSIGNED; ptx_lval.int_value = atoi(yytext); return INT_OPERAND;
+[-]?[0-9]+U? TC; CHECK_UNSIGNED; yylval->int_value = atoi(yytext); return INT_OPERAND;
-0[fF][0-9a-fA-F]{8} TC; sscanf(yytext+2,"%x", (unsigned*)(void*)&ptx_lval.float_value); return FLOAT_OPERAND;
-0[dD][0-9a-fA-F]{16} TC; sscanf(yytext+2,"%Lx", (unsigned long long*)(void*)&ptx_lval.double_value); return DOUBLE_OPERAND;
+0[fF][0-9a-fA-F]{8} TC; sscanf(yytext+2,"%x", (unsigned*)(void*)&yylval->float_value); return FLOAT_OPERAND;
+0[dD][0-9a-fA-F]{16} TC; sscanf(yytext+2,"%Lx", (unsigned long long*)(void*)&yylval->double_value); return DOUBLE_OPERAND;
\.s8 TC; return S8_TYPE;
\.s16 TC; return S16_TYPE;
@@ -385,12 +392,12 @@ breakaddr TC; ptx_lval.int_value = BREAKADDR_OP; return OPCODE;
\.2d TC; return GEOM_MODIFIER_2D;
\.3d TC; return GEOM_MODIFIER_3D;
-\.0 TC; ptx_lval.int_value = 0; return DIMENSION_MODIFIER;
-\.1 TC; ptx_lval.int_value = 1; return DIMENSION_MODIFIER;
-\.2 TC; ptx_lval.int_value = 2; return DIMENSION_MODIFIER;
-\.x TC; ptx_lval.int_value = 0; return DIMENSION_MODIFIER;
-\.y TC; ptx_lval.int_value = 1; return DIMENSION_MODIFIER;
-\.z TC; ptx_lval.int_value = 2; return DIMENSION_MODIFIER;
+\.0 TC; yylval->int_value = 0; return DIMENSION_MODIFIER;
+\.1 TC; yylval->int_value = 1; return DIMENSION_MODIFIER;
+\.2 TC; yylval->int_value = 2; return DIMENSION_MODIFIER;
+\.x TC; yylval->int_value = 0; return DIMENSION_MODIFIER;
+\.y TC; yylval->int_value = 1; return DIMENSION_MODIFIER;
+\.z TC; yylval->int_value = 2; return DIMENSION_MODIFIER;
"-" TC; return MINUS;
"+" TC; return PLUS;
@@ -413,7 +420,7 @@ breakaddr TC; ptx_lval.int_value = BREAKADDR_OP; return OPCODE;
"//"[^\n]* TC; // eat single
-\n.* col=0; strncpy(linebuf, yytext + 1, LINEBUF_SIZE); yyless( 1 );
+\n.* recognizer->col=0; strncpy(recognizer->linebuf, yytext + 1, LINEBUF_SIZE); yyless( 1 );
" " TC;
"\t" TC;
@@ -441,28 +448,26 @@ breakaddr TC; ptx_lval.int_value = BREAKADDR_OP; return OPCODE;
}
<IN_STRING>{
"\"" TC; BEGIN(INITIAL); return STRING;
-[^\"]* TC; ptx_lval.string_value = strdup(yytext);
+[^\"]* TC; yylval->string_value = strdup(yytext);
}
<*>\t@@DWARF.*\n
-<INITIAL,NOT_OPCODE,IN_FUNC_DECL>. TC; ptx_error((const char*)NULL);
+<INITIAL,NOT_OPCODE,IN_FUNC_DECL>. TC; ptx_error(yyscanner, recognizer, (const char*)NULL);
%%
-extern int g_error_detected;
-extern const char *g_filename;
-
-int ptx_error( const char *s )
+int ptx_error( yyscan_t yyscanner, ptx_recognizer* recognizer, const char *s )
{
+ struct yyguts_t * yyg = (struct yyguts_t*)yyscanner;
int i;
- g_error_detected = 1;
+ recognizer->g_error_detected = 1;
fflush(stdout);
if( s != NULL )
- printf("%s:%u: Syntax error:\n\n", g_filename, ptx_lineno );
- printf(" %s\n", linebuf );
+ printf("%s:%u Syntax error:\n\n", recognizer->gpgpu_ctx->g_filename, yylineno );
+ printf(" %s\n", recognizer->linebuf );
printf(" ");
- for( i=0; i < col-1; i++ ) {
- if( linebuf[i] == '\t' ) printf("\t");
+ for( i=0; i < recognizer->col-1; i++ ) {
+ if( recognizer->linebuf[i] == '\t' ) printf("\t");
else printf(" ");
}
diff --git a/src/cuda-sim/ptx.y b/src/cuda-sim/ptx.y
index 45392fb..a01c3c6 100644
--- a/src/cuda-sim/ptx.y
+++ b/src/cuda-sim/ptx.y
@@ -27,6 +27,18 @@ OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
+%{
+typedef void * yyscan_t;
+class ptx_recognizer;
+#include "../../libcuda/gpgpu_context.h"
+%}
+
+%define api.pure full
+%parse-param {yyscan_t scanner}
+%parse-param {ptx_recognizer* recognizer}
+%lex-param {yyscan_t scanner}
+%lex-param {ptx_recognizer* recognizer}
+
%union {
double double_value;
float float_value;
@@ -217,10 +229,9 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#include <stdlib.h>
#include <string.h>
#include <math.h>
- void syntax_not_implemented();
- extern int g_func_decl;
- int ptx_lex(void);
- int ptx_error(const char *);
+ void syntax_not_implemented(yyscan_t yyscanner, ptx_recognizer* recognizer);
+ int ptx_lex(YYSTYPE * yylval_param, yyscan_t yyscanner, ptx_recognizer* recognizer);
+ int ptx_error( yyscan_t yyscanner, ptx_recognizer* recognizer, const char *s );
%}
%%
@@ -231,96 +242,96 @@ input: /* empty */
| input function_decl
;
-function_defn: function_decl { set_symtab($1); func_header(".skip"); } statement_block { end_function(); }
- | function_decl { set_symtab($1); } block_spec_list { func_header(".skip"); } statement_block { end_function(); }
+function_defn: function_decl { recognizer->set_symtab($1); recognizer->func_header(".skip"); } statement_block { recognizer->end_function(); }
+ | function_decl { recognizer->set_symtab($1); } block_spec_list { recognizer->func_header(".skip"); } statement_block { recognizer->end_function(); }
;
-block_spec: MAXNTID_DIRECTIVE INT_OPERAND COMMA INT_OPERAND COMMA INT_OPERAND {func_header_info_int(".maxntid", $2);
- func_header_info_int(",", $4);
- func_header_info_int(",", $6);
- maxnt_id($2, $4, $6);}
- | MINNCTAPERSM_DIRECTIVE INT_OPERAND { func_header_info_int(".minnctapersm", $2); printf("GPGPU-Sim: Warning: .minnctapersm ignored. \n"); }
- | MAXNCTAPERSM_DIRECTIVE INT_OPERAND { func_header_info_int(".maxnctapersm", $2); printf("GPGPU-Sim: Warning: .maxnctapersm ignored. \n"); }
+block_spec: MAXNTID_DIRECTIVE INT_OPERAND COMMA INT_OPERAND COMMA INT_OPERAND {recognizer->func_header_info_int(".maxntid", $2);
+ recognizer->func_header_info_int(",", $4);
+ recognizer->func_header_info_int(",", $6);
+ recognizer->maxnt_id($2, $4, $6);}
+ | MINNCTAPERSM_DIRECTIVE INT_OPERAND { recognizer->func_header_info_int(".minnctapersm", $2); printf("GPGPU-Sim: Warning: .minnctapersm ignored. \n"); }
+ | MAXNCTAPERSM_DIRECTIVE INT_OPERAND { recognizer->func_header_info_int(".maxnctapersm", $2); printf("GPGPU-Sim: Warning: .maxnctapersm ignored. \n"); }
;
block_spec_list: block_spec
| block_spec_list block_spec
;
-function_decl: function_decl_header LEFT_PAREN { start_function($1); func_header_info("(");} param_entry RIGHT_PAREN {func_header_info(")");} function_ident_param { $$ = reset_symtab(); }
- | function_decl_header { start_function($1); } function_ident_param { $$ = reset_symtab(); }
- | function_decl_header { start_function($1); add_function_name(""); g_func_decl=0; $$ = reset_symtab(); }
+function_decl: function_decl_header LEFT_PAREN { recognizer->start_function($1); recognizer->func_header_info("(");} param_entry RIGHT_PAREN {recognizer->func_header_info(")");} function_ident_param { $$ = recognizer->reset_symtab(); }
+ | function_decl_header { recognizer->start_function($1); } function_ident_param { $$ = recognizer->reset_symtab(); }
+ | function_decl_header { recognizer->start_function($1); recognizer->add_function_name(""); recognizer->g_func_decl=0; $$ = recognizer->reset_symtab(); }
;
-function_ident_param: IDENTIFIER { add_function_name($1); } LEFT_PAREN {func_header_info("(");} param_list RIGHT_PAREN { g_func_decl=0; func_header_info(")"); }
- | IDENTIFIER { add_function_name($1); g_func_decl=0; }
+function_ident_param: IDENTIFIER { recognizer->add_function_name($1); } LEFT_PAREN {recognizer->func_header_info("(");} param_list RIGHT_PAREN { recognizer->g_func_decl=0; recognizer->func_header_info(")"); }
+ | IDENTIFIER { recognizer->add_function_name($1); recognizer->g_func_decl=0; }
;
-function_decl_header: ENTRY_DIRECTIVE { $$ = 1; g_func_decl=1; func_header(".entry"); }
- | VISIBLE_DIRECTIVE ENTRY_DIRECTIVE { $$ = 1; g_func_decl=1; func_header(".entry"); }
- | WEAK_DIRECTIVE ENTRY_DIRECTIVE { $$ = 1; g_func_decl=1; func_header(".entry"); }
- | FUNC_DIRECTIVE { $$ = 0; g_func_decl=1; func_header(".func"); }
- | VISIBLE_DIRECTIVE FUNC_DIRECTIVE { $$ = 0; g_func_decl=1; func_header(".func"); }
- | WEAK_DIRECTIVE FUNC_DIRECTIVE { $$ = 0; g_func_decl=1; func_header(".func"); }
- | EXTERN_DIRECTIVE FUNC_DIRECTIVE { $$ = 2; g_func_decl=1; func_header(".func"); }
- | WEAK_DIRECTIVE FUNC_DIRECTIVE { $$ = 0; g_func_decl=1; func_header(".func"); }
+function_decl_header: ENTRY_DIRECTIVE { $$ = 1; recognizer->g_func_decl=1; recognizer->func_header(".entry"); }
+ | VISIBLE_DIRECTIVE ENTRY_DIRECTIVE { $$ = 1; recognizer->g_func_decl=1; recognizer->func_header(".entry"); }
+ | WEAK_DIRECTIVE ENTRY_DIRECTIVE { $$ = 1; recognizer->g_func_decl=1; recognizer->func_header(".entry"); }
+ | FUNC_DIRECTIVE { $$ = 0; recognizer->g_func_decl=1; recognizer->func_header(".func"); }
+ | VISIBLE_DIRECTIVE FUNC_DIRECTIVE { $$ = 0; recognizer->g_func_decl=1; recognizer->func_header(".func"); }
+ | WEAK_DIRECTIVE FUNC_DIRECTIVE { $$ = 0; recognizer->g_func_decl=1; recognizer->func_header(".func"); }
+ | EXTERN_DIRECTIVE FUNC_DIRECTIVE { $$ = 2; recognizer->g_func_decl=1; recognizer->func_header(".func"); }
+ | WEAK_DIRECTIVE FUNC_DIRECTIVE { $$ = 0; recognizer->g_func_decl=1; recognizer->func_header(".func"); }
;
param_list: /*empty*/
- | param_entry { add_directive(); }
- | param_list COMMA {func_header_info(",");} param_entry { add_directive(); }
+ | param_entry { recognizer->add_directive(); }
+ | param_list COMMA {recognizer->func_header_info(",");} param_entry { recognizer->add_directive(); }
-param_entry: PARAM_DIRECTIVE { add_space_spec(param_space_unclassified,0); } variable_spec ptr_spec identifier_spec { add_function_arg(); }
- | REG_DIRECTIVE { add_space_spec(reg_space,0); } variable_spec identifier_spec { add_function_arg(); }
+param_entry: PARAM_DIRECTIVE { recognizer->add_space_spec(param_space_unclassified,0); } variable_spec ptr_spec identifier_spec { recognizer->add_function_arg(); }
+ | REG_DIRECTIVE { recognizer->add_space_spec(reg_space,0); } variable_spec identifier_spec { recognizer->add_function_arg(); }
ptr_spec: /*empty*/
| PTR_DIRECTIVE ptr_space_spec ptr_align_spec
| PTR_DIRECTIVE ptr_align_spec
-ptr_space_spec: GLOBAL_DIRECTIVE { add_ptr_spec(global_space); }
- | LOCAL_DIRECTIVE { add_ptr_spec(local_space); }
- | SHARED_DIRECTIVE { add_ptr_spec(shared_space); }
- | CONST_DIRECTIVE { add_ptr_spec(global_space); }
+ptr_space_spec: GLOBAL_DIRECTIVE { recognizer->add_ptr_spec(global_space); }
+ | LOCAL_DIRECTIVE { recognizer->add_ptr_spec(local_space); }
+ | SHARED_DIRECTIVE { recognizer->add_ptr_spec(shared_space); }
+ | CONST_DIRECTIVE { recognizer->add_ptr_spec(global_space); }
ptr_align_spec: ALIGN_DIRECTIVE INT_OPERAND
statement_block: LEFT_BRACE statement_list RIGHT_BRACE
-statement_list: directive_statement { add_directive(); }
- | instruction_statement { add_instruction(); }
- | statement_list directive_statement { add_directive(); }
- | statement_list instruction_statement { add_instruction(); }
- | statement_list {start_inst_group();} statement_block {end_inst_group();}
- | {start_inst_group();} statement_block {end_inst_group();}
+statement_list: directive_statement { recognizer->add_directive(); }
+ | instruction_statement { recognizer->add_instruction(); }
+ | statement_list directive_statement { recognizer->add_directive(); }
+ | statement_list instruction_statement { recognizer->add_instruction(); }
+ | statement_list {recognizer->start_inst_group();} statement_block {recognizer->end_inst_group();}
+ | {recognizer->start_inst_group();} statement_block {recognizer->end_inst_group();}
;
directive_statement: variable_declaration SEMI_COLON
- | VERSION_DIRECTIVE DOUBLE_OPERAND { add_version_info($2, 0); }
- | VERSION_DIRECTIVE DOUBLE_OPERAND PLUS { add_version_info($2,1); }
+ | VERSION_DIRECTIVE DOUBLE_OPERAND { recognizer->add_version_info($2, 0); }
+ | VERSION_DIRECTIVE DOUBLE_OPERAND PLUS { recognizer->add_version_info($2,1); }
| ADDRESS_SIZE_DIRECTIVE INT_OPERAND {/*Do nothing*/}
- | TARGET_DIRECTIVE IDENTIFIER COMMA IDENTIFIER { target_header2($2,$4); }
- | TARGET_DIRECTIVE IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER { target_header3($2,$4,$6); }
- | TARGET_DIRECTIVE IDENTIFIER { target_header($2); }
- | FILE_DIRECTIVE INT_OPERAND STRING { add_file($2,$3); }
- | FILE_DIRECTIVE INT_OPERAND STRING COMMA INT_OPERAND COMMA INT_OPERAND { add_file($2,$3); }
+ | TARGET_DIRECTIVE IDENTIFIER COMMA IDENTIFIER { recognizer->target_header2($2,$4); }
+ | TARGET_DIRECTIVE IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER { recognizer->target_header3($2,$4,$6); }
+ | TARGET_DIRECTIVE IDENTIFIER { recognizer->target_header($2); }
+ | FILE_DIRECTIVE INT_OPERAND STRING { recognizer->add_file($2,$3); }
+ | FILE_DIRECTIVE INT_OPERAND STRING COMMA INT_OPERAND COMMA INT_OPERAND { recognizer->add_file($2,$3); }
| LOC_DIRECTIVE INT_OPERAND INT_OPERAND INT_OPERAND
- | PRAGMA_DIRECTIVE STRING SEMI_COLON { add_pragma($2); }
+ | PRAGMA_DIRECTIVE STRING SEMI_COLON { recognizer->add_pragma($2); }
| function_decl SEMI_COLON {/*Do nothing*/}
;
-variable_declaration: variable_spec identifier_list { add_variables(); }
- | variable_spec identifier_spec EQUALS initializer_list { add_variables(); }
- | variable_spec identifier_spec EQUALS literal_operand { add_variables(); }
- | CONSTPTR_DIRECTIVE IDENTIFIER COMMA IDENTIFIER COMMA INT_OPERAND { add_constptr($2, $4, $6); }
+variable_declaration: variable_spec identifier_list { recognizer->add_variables(); }
+ | variable_spec identifier_spec EQUALS initializer_list { recognizer->add_variables(); }
+ | variable_spec identifier_spec EQUALS literal_operand { recognizer->add_variables(); }
+ | CONSTPTR_DIRECTIVE IDENTIFIER COMMA IDENTIFIER COMMA INT_OPERAND { recognizer->add_constptr($2, $4, $6); }
;
-variable_spec: var_spec_list { set_variable_type(); }
+variable_spec: var_spec_list { recognizer->set_variable_type(); }
identifier_list: identifier_spec
| identifier_list COMMA identifier_spec;
-identifier_spec: IDENTIFIER { add_identifier($1,0,NON_ARRAY_IDENTIFIER); func_header_info($1);}
- | IDENTIFIER LEFT_ANGLE_BRACKET INT_OPERAND RIGHT_ANGLE_BRACKET { func_header_info($1); func_header_info_int("<", $3); func_header_info(">");
+identifier_spec: IDENTIFIER { recognizer->add_identifier($1,0,NON_ARRAY_IDENTIFIER); recognizer->func_header_info($1);}
+ | IDENTIFIER LEFT_ANGLE_BRACKET INT_OPERAND RIGHT_ANGLE_BRACKET { recognizer->func_header_info($1); recognizer->func_header_info_int("<", $3); recognizer->func_header_info(">");
int i,lbase,l;
char *id = NULL;
lbase = strlen($1);
@@ -328,12 +339,12 @@ identifier_spec: IDENTIFIER { add_identifier($1,0,NON_ARRAY_IDENTIFIER); func_he
l = lbase + (int)log10(i+1)+10;
id = (char*) malloc(l);
snprintf(id,l,"%s%u",$1,i);
- add_identifier(id,0,NON_ARRAY_IDENTIFIER);
+ recognizer->add_identifier(id,0,NON_ARRAY_IDENTIFIER);
}
free($1);
}
- | IDENTIFIER LEFT_SQUARE_BRACKET RIGHT_SQUARE_BRACKET { add_identifier($1,0,ARRAY_IDENTIFIER_NO_DIM); func_header_info($1); func_header_info("["); func_header_info("]");}
- | IDENTIFIER LEFT_SQUARE_BRACKET INT_OPERAND RIGHT_SQUARE_BRACKET { add_identifier($1,$3,ARRAY_IDENTIFIER); func_header_info($1); func_header_info_int("[",$3); func_header_info("]");}
+ | IDENTIFIER LEFT_SQUARE_BRACKET RIGHT_SQUARE_BRACKET { recognizer->add_identifier($1,0,ARRAY_IDENTIFIER_NO_DIM); recognizer->func_header_info($1); recognizer->func_header_info("["); recognizer->func_header_info("]");}
+ | IDENTIFIER LEFT_SQUARE_BRACKET INT_OPERAND RIGHT_SQUARE_BRACKET { recognizer->add_identifier($1,$3,ARRAY_IDENTIFIER); recognizer->func_header_info($1); recognizer->func_header_info_int("[",$3); recognizer->func_header_info("]");}
;
var_spec_list: var_spec
@@ -343,93 +354,93 @@ var_spec: space_spec
| type_spec
| align_spec
| VISIBLE_DIRECTIVE
- | EXTERN_DIRECTIVE { add_extern_spec(); }
+ | EXTERN_DIRECTIVE { recognizer->add_extern_spec(); }
| WEAK_DIRECTIVE
;
-align_spec: ALIGN_DIRECTIVE INT_OPERAND { add_alignment_spec($2); }
+align_spec: ALIGN_DIRECTIVE INT_OPERAND { recognizer->add_alignment_spec($2); }
-space_spec: REG_DIRECTIVE { add_space_spec(reg_space,0); }
- | SREG_DIRECTIVE { add_space_spec(reg_space,0); }
+space_spec: REG_DIRECTIVE { recognizer->add_space_spec(reg_space,0); }
+ | SREG_DIRECTIVE { recognizer->add_space_spec(reg_space,0); }
| addressable_spec
;
-addressable_spec: CONST_DIRECTIVE { add_space_spec(const_space,$1); }
- | GLOBAL_DIRECTIVE { add_space_spec(global_space,0); }
- | LOCAL_DIRECTIVE { add_space_spec(local_space,0); }
- | PARAM_DIRECTIVE { add_space_spec(param_space_unclassified,0); }
- | SHARED_DIRECTIVE { add_space_spec(shared_space,0); }
- | SSTARR_DIRECTIVE { add_space_spec(sstarr_space,0); }
- | SURF_DIRECTIVE { add_space_spec(surf_space,0); }
- | TEX_DIRECTIVE { add_space_spec(tex_space,0); }
+addressable_spec: CONST_DIRECTIVE { recognizer->add_space_spec(const_space,$1); }
+ | GLOBAL_DIRECTIVE { recognizer->add_space_spec(global_space,0); }
+ | LOCAL_DIRECTIVE { recognizer->add_space_spec(local_space,0); }
+ | PARAM_DIRECTIVE { recognizer->add_space_spec(param_space_unclassified,0); }
+ | SHARED_DIRECTIVE { recognizer->add_space_spec(shared_space,0); }
+ | SSTARR_DIRECTIVE { recognizer->add_space_spec(sstarr_space,0); }
+ | SURF_DIRECTIVE { recognizer->add_space_spec(surf_space,0); }
+ | TEX_DIRECTIVE { recognizer->add_space_spec(tex_space,0); }
;
type_spec: scalar_type
| vector_spec scalar_type
;
-vector_spec: V2_TYPE { add_option(V2_TYPE); func_header_info(".v2");}
- | V3_TYPE { add_option(V3_TYPE); func_header_info(".v3");}
- | V4_TYPE { add_option(V4_TYPE); func_header_info(".v4");}
+vector_spec: V2_TYPE { recognizer->add_option(V2_TYPE); recognizer->func_header_info(".v2");}
+ | V3_TYPE { recognizer->add_option(V3_TYPE); recognizer->func_header_info(".v3");}
+ | V4_TYPE { recognizer->add_option(V4_TYPE); recognizer->func_header_info(".v4");}
;
-scalar_type: S8_TYPE { add_scalar_type_spec( S8_TYPE ); }
- | S16_TYPE { add_scalar_type_spec( S16_TYPE ); }
- | S32_TYPE { add_scalar_type_spec( S32_TYPE ); }
- | S64_TYPE { add_scalar_type_spec( S64_TYPE ); }
- | U8_TYPE { add_scalar_type_spec( U8_TYPE ); }
- | U16_TYPE { add_scalar_type_spec( U16_TYPE ); }
- | U32_TYPE { add_scalar_type_spec( U32_TYPE ); }
- | U64_TYPE { add_scalar_type_spec( U64_TYPE ); }
- | F16_TYPE { add_scalar_type_spec( F16_TYPE ); }
- | F32_TYPE { add_scalar_type_spec( F32_TYPE ); }
- | F64_TYPE { add_scalar_type_spec( F64_TYPE ); }
- | FF64_TYPE { add_scalar_type_spec( FF64_TYPE ); }
- | B8_TYPE { add_scalar_type_spec( B8_TYPE ); }
- | B16_TYPE { add_scalar_type_spec( B16_TYPE ); }
- | B32_TYPE { add_scalar_type_spec( B32_TYPE ); }
- | B64_TYPE { add_scalar_type_spec( B64_TYPE ); }
- | BB64_TYPE { add_scalar_type_spec( BB64_TYPE ); }
- | BB128_TYPE { add_scalar_type_spec( BB128_TYPE ); }
- | PRED_TYPE { add_scalar_type_spec( PRED_TYPE ); }
- | TEXREF_TYPE { add_scalar_type_spec( TEXREF_TYPE ); }
- | SAMPLERREF_TYPE { add_scalar_type_spec( SAMPLERREF_TYPE ); }
- | SURFREF_TYPE { add_scalar_type_spec( SURFREF_TYPE ); }
+scalar_type: S8_TYPE { recognizer->add_scalar_type_spec( S8_TYPE ); }
+ | S16_TYPE { recognizer->add_scalar_type_spec( S16_TYPE ); }
+ | S32_TYPE { recognizer->add_scalar_type_spec( S32_TYPE ); }
+ | S64_TYPE { recognizer->add_scalar_type_spec( S64_TYPE ); }
+ | U8_TYPE { recognizer->add_scalar_type_spec( U8_TYPE ); }
+ | U16_TYPE { recognizer->add_scalar_type_spec( U16_TYPE ); }
+ | U32_TYPE { recognizer->add_scalar_type_spec( U32_TYPE ); }
+ | U64_TYPE { recognizer->add_scalar_type_spec( U64_TYPE ); }
+ | F16_TYPE { recognizer->add_scalar_type_spec( F16_TYPE ); }
+ | F32_TYPE { recognizer->add_scalar_type_spec( F32_TYPE ); }
+ | F64_TYPE { recognizer->add_scalar_type_spec( F64_TYPE ); }
+ | FF64_TYPE { recognizer->add_scalar_type_spec( FF64_TYPE ); }
+ | B8_TYPE { recognizer->add_scalar_type_spec( B8_TYPE ); }
+ | B16_TYPE { recognizer->add_scalar_type_spec( B16_TYPE ); }
+ | B32_TYPE { recognizer->add_scalar_type_spec( B32_TYPE ); }
+ | B64_TYPE { recognizer->add_scalar_type_spec( B64_TYPE ); }
+ | BB64_TYPE { recognizer->add_scalar_type_spec( BB64_TYPE ); }
+ | BB128_TYPE { recognizer->add_scalar_type_spec( BB128_TYPE ); }
+ | PRED_TYPE { recognizer->add_scalar_type_spec( PRED_TYPE ); }
+ | TEXREF_TYPE { recognizer->add_scalar_type_spec( TEXREF_TYPE ); }
+ | SAMPLERREF_TYPE { recognizer->add_scalar_type_spec( SAMPLERREF_TYPE ); }
+ | SURFREF_TYPE { recognizer->add_scalar_type_spec( SURFREF_TYPE ); }
;
-initializer_list: LEFT_BRACE literal_list RIGHT_BRACE { add_array_initializer(); }
- | LEFT_BRACE initializer_list RIGHT_BRACE { syntax_not_implemented(); }
+initializer_list: LEFT_BRACE literal_list RIGHT_BRACE { recognizer->add_array_initializer(); }
+ | LEFT_BRACE initializer_list RIGHT_BRACE { syntax_not_implemented(scanner, recognizer); }
literal_list: literal_operand
| literal_list COMMA literal_operand;
instruction_statement: instruction SEMI_COLON
- | IDENTIFIER COLON { add_label($1); }
+ | IDENTIFIER COLON { recognizer->add_label($1); }
| pred_spec instruction SEMI_COLON;
-instruction: opcode_spec LEFT_PAREN operand RIGHT_PAREN { set_return(); } COMMA operand COMMA LEFT_PAREN operand_list RIGHT_PAREN
+instruction: opcode_spec LEFT_PAREN operand RIGHT_PAREN { recognizer->set_return(); } COMMA operand COMMA LEFT_PAREN operand_list RIGHT_PAREN
| opcode_spec operand COMMA LEFT_PAREN operand_list RIGHT_PAREN
| opcode_spec operand COMMA LEFT_PAREN RIGHT_PAREN
| opcode_spec operand_list
| opcode_spec
;
-opcode_spec: OPCODE { add_opcode($1); } option_list
- | OPCODE { add_opcode($1); }
+opcode_spec: OPCODE { recognizer->add_opcode($1); } option_list
+ | OPCODE { recognizer->add_opcode($1); }
-pred_spec: PRED IDENTIFIER { add_pred($2,0, -1); }
- | PRED EXCLAMATION IDENTIFIER { add_pred($3,1, -1); }
- | PRED IDENTIFIER LT_OPTION { add_pred($2,0,1); }
- | PRED IDENTIFIER EQ_OPTION { add_pred($2,0,2); }
- | PRED IDENTIFIER LE_OPTION { add_pred($2,0,3); }
- | PRED IDENTIFIER NE_OPTION { add_pred($2,0,5); }
- | PRED IDENTIFIER GE_OPTION { add_pred($2,0,6); }
- | PRED IDENTIFIER EQU_OPTION { add_pred($2,0,10); }
- | PRED IDENTIFIER GTU_OPTION { add_pred($2,0,12); }
- | PRED IDENTIFIER NEU_OPTION { add_pred($2,0,13); }
- | PRED IDENTIFIER CF_OPTION { add_pred($2,0,17); }
- | PRED IDENTIFIER SF_OPTION { add_pred($2,0,19); }
- | PRED IDENTIFIER NSF_OPTION { add_pred($2,0,28); }
+pred_spec: PRED IDENTIFIER { recognizer->add_pred($2,0, -1); }
+ | PRED EXCLAMATION IDENTIFIER { recognizer->add_pred($3,1, -1); }
+ | PRED IDENTIFIER LT_OPTION { recognizer->add_pred($2,0,1); }
+ | PRED IDENTIFIER EQ_OPTION { recognizer->add_pred($2,0,2); }
+ | PRED IDENTIFIER LE_OPTION { recognizer->add_pred($2,0,3); }
+ | PRED IDENTIFIER NE_OPTION { recognizer->add_pred($2,0,5); }
+ | PRED IDENTIFIER GE_OPTION { recognizer->add_pred($2,0,6); }
+ | PRED IDENTIFIER EQU_OPTION { recognizer->add_pred($2,0,10); }
+ | PRED IDENTIFIER GTU_OPTION { recognizer->add_pred($2,0,12); }
+ | PRED IDENTIFIER NEU_OPTION { recognizer->add_pred($2,0,13); }
+ | PRED IDENTIFIER CF_OPTION { recognizer->add_pred($2,0,17); }
+ | PRED IDENTIFIER SF_OPTION { recognizer->add_pred($2,0,19); }
+ | PRED IDENTIFIER NSF_OPTION { recognizer->add_pred($2,0,28); }
;
option_list: option
@@ -441,108 +452,108 @@ option: type_spec
| rounding_mode
| wmma_spec
| prmt_spec
- | SYNC_OPTION { add_option(SYNC_OPTION); }
- | ARRIVE_OPTION { add_option(ARRIVE_OPTION); }
- | RED_OPTION { add_option(RED_OPTION); }
- | UNI_OPTION { add_option(UNI_OPTION); }
- | WIDE_OPTION { add_option(WIDE_OPTION); }
- | ANY_OPTION { add_option(ANY_OPTION); }
- | ALL_OPTION { add_option(ALL_OPTION); }
- | BALLOT_OPTION { add_option(BALLOT_OPTION); }
- | GLOBAL_OPTION { add_option(GLOBAL_OPTION); }
- | CTA_OPTION { add_option(CTA_OPTION); }
- | SYS_OPTION { add_option(SYS_OPTION); }
- | GEOM_MODIFIER_1D { add_option(GEOM_MODIFIER_1D); }
- | GEOM_MODIFIER_2D { add_option(GEOM_MODIFIER_2D); }
- | GEOM_MODIFIER_3D { add_option(GEOM_MODIFIER_3D); }
- | SAT_OPTION { add_option(SAT_OPTION); }
- | FTZ_OPTION { add_option(FTZ_OPTION); }
- | NEG_OPTION { add_option(NEG_OPTION); }
- | APPROX_OPTION { add_option(APPROX_OPTION); }
- | FULL_OPTION { add_option(FULL_OPTION); }
- | EXIT_OPTION { add_option(EXIT_OPTION); }
- | ABS_OPTION { add_option(ABS_OPTION); }
+ | SYNC_OPTION { recognizer->add_option(SYNC_OPTION); }
+ | ARRIVE_OPTION { recognizer->add_option(ARRIVE_OPTION); }
+ | RED_OPTION { recognizer->add_option(RED_OPTION); }
+ | UNI_OPTION { recognizer->add_option(UNI_OPTION); }
+ | WIDE_OPTION { recognizer->add_option(WIDE_OPTION); }
+ | ANY_OPTION { recognizer->add_option(ANY_OPTION); }
+ | ALL_OPTION { recognizer->add_option(ALL_OPTION); }
+ | BALLOT_OPTION { recognizer->add_option(BALLOT_OPTION); }
+ | GLOBAL_OPTION { recognizer->add_option(GLOBAL_OPTION); }
+ | CTA_OPTION { recognizer->add_option(CTA_OPTION); }
+ | SYS_OPTION { recognizer->add_option(SYS_OPTION); }
+ | GEOM_MODIFIER_1D { recognizer->add_option(GEOM_MODIFIER_1D); }
+ | GEOM_MODIFIER_2D { recognizer->add_option(GEOM_MODIFIER_2D); }
+ | GEOM_MODIFIER_3D { recognizer->add_option(GEOM_MODIFIER_3D); }
+ | SAT_OPTION { recognizer->add_option(SAT_OPTION); }
+ | FTZ_OPTION { recognizer->add_option(FTZ_OPTION); }
+ | NEG_OPTION { recognizer->add_option(NEG_OPTION); }
+ | APPROX_OPTION { recognizer->add_option(APPROX_OPTION); }
+ | FULL_OPTION { recognizer->add_option(FULL_OPTION); }
+ | EXIT_OPTION { recognizer->add_option(EXIT_OPTION); }
+ | ABS_OPTION { recognizer->add_option(ABS_OPTION); }
| atomic_operation_spec ;
- | TO_OPTION { add_option(TO_OPTION); }
- | HALF_OPTION { add_option(HALF_OPTION); }
- | EXTP_OPTION { add_option(EXTP_OPTION); }
- | CA_OPTION { add_option(CA_OPTION); }
- | CG_OPTION { add_option(CG_OPTION); }
- | CS_OPTION { add_option(CS_OPTION); }
- | LU_OPTION { add_option(LU_OPTION); }
- | CV_OPTION { add_option(CV_OPTION); }
- | WB_OPTION { add_option(WB_OPTION); }
- | WT_OPTION { add_option(WT_OPTION); }
- | NC_OPTION { add_option(NC_OPTION); }
- | UP_OPTION { add_option(UP_OPTION); }
- | DOWN_OPTION { add_option(DOWN_OPTION); }
- | BFLY_OPTION { add_option(BFLY_OPTION); }
- | IDX_OPTION { add_option(IDX_OPTION); }
+ | TO_OPTION { recognizer->add_option(TO_OPTION); }
+ | HALF_OPTION { recognizer->add_option(HALF_OPTION); }
+ | EXTP_OPTION { recognizer->add_option(EXTP_OPTION); }
+ | CA_OPTION { recognizer->add_option(CA_OPTION); }
+ | CG_OPTION { recognizer->add_option(CG_OPTION); }
+ | CS_OPTION { recognizer->add_option(CS_OPTION); }
+ | LU_OPTION { recognizer->add_option(LU_OPTION); }
+ | CV_OPTION { recognizer->add_option(CV_OPTION); }
+ | WB_OPTION { recognizer->add_option(WB_OPTION); }
+ | WT_OPTION { recognizer->add_option(WT_OPTION); }
+ | NC_OPTION { recognizer->add_option(NC_OPTION); }
+ | UP_OPTION { recognizer->add_option(UP_OPTION); }
+ | DOWN_OPTION { recognizer->add_option(DOWN_OPTION); }
+ | BFLY_OPTION { recognizer->add_option(BFLY_OPTION); }
+ | IDX_OPTION { recognizer->add_option(IDX_OPTION); }
;
-atomic_operation_spec: ATOMIC_AND { add_option(ATOMIC_AND); }
- | ATOMIC_POPC { add_option(ATOMIC_POPC); }
- | ATOMIC_OR { add_option(ATOMIC_OR); }
- | ATOMIC_XOR { add_option(ATOMIC_XOR); }
- | ATOMIC_CAS { add_option(ATOMIC_CAS); }
- | ATOMIC_EXCH { add_option(ATOMIC_EXCH); }
- | ATOMIC_ADD { add_option(ATOMIC_ADD); }
- | ATOMIC_INC { add_option(ATOMIC_INC); }
- | ATOMIC_DEC { add_option(ATOMIC_DEC); }
- | ATOMIC_MIN { add_option(ATOMIC_MIN); }
- | ATOMIC_MAX { add_option(ATOMIC_MAX); }
+atomic_operation_spec: ATOMIC_AND { recognizer->add_option(ATOMIC_AND); }
+ | ATOMIC_POPC { recognizer->add_option(ATOMIC_POPC); }
+ | ATOMIC_OR { recognizer->add_option(ATOMIC_OR); }
+ | ATOMIC_XOR { recognizer->add_option(ATOMIC_XOR); }
+ | ATOMIC_CAS { recognizer->add_option(ATOMIC_CAS); }
+ | ATOMIC_EXCH { recognizer->add_option(ATOMIC_EXCH); }
+ | ATOMIC_ADD { recognizer->add_option(ATOMIC_ADD); }
+ | ATOMIC_INC { recognizer->add_option(ATOMIC_INC); }
+ | ATOMIC_DEC { recognizer->add_option(ATOMIC_DEC); }
+ | ATOMIC_MIN { recognizer->add_option(ATOMIC_MIN); }
+ | ATOMIC_MAX { recognizer->add_option(ATOMIC_MAX); }
;
rounding_mode: floating_point_rounding_mode
| integer_rounding_mode;
-floating_point_rounding_mode: RN_OPTION { add_option(RN_OPTION); }
- | RZ_OPTION { add_option(RZ_OPTION); }
- | RM_OPTION { add_option(RM_OPTION); }
- | RP_OPTION { add_option(RP_OPTION); }
+floating_point_rounding_mode: RN_OPTION { recognizer->add_option(RN_OPTION); }
+ | RZ_OPTION { recognizer->add_option(RZ_OPTION); }
+ | RM_OPTION { recognizer->add_option(RM_OPTION); }
+ | RP_OPTION { recognizer->add_option(RP_OPTION); }
;
-integer_rounding_mode: RNI_OPTION { add_option(RNI_OPTION); }
- | RZI_OPTION { add_option(RZI_OPTION); }
- | RMI_OPTION { add_option(RMI_OPTION); }
- | RPI_OPTION { add_option(RPI_OPTION); }
+integer_rounding_mode: RNI_OPTION { recognizer->add_option(RNI_OPTION); }
+ | RZI_OPTION { recognizer->add_option(RZI_OPTION); }
+ | RMI_OPTION { recognizer->add_option(RMI_OPTION); }
+ | RPI_OPTION { recognizer->add_option(RPI_OPTION); }
;
-compare_spec:EQ_OPTION { add_option(EQ_OPTION); }
- | NE_OPTION { add_option(NE_OPTION); }
- | LT_OPTION { add_option(LT_OPTION); }
- | LE_OPTION { add_option(LE_OPTION); }
- | GT_OPTION { add_option(GT_OPTION); }
- | GE_OPTION { add_option(GE_OPTION); }
- | LO_OPTION { add_option(LO_OPTION); }
- | LS_OPTION { add_option(LS_OPTION); }
- | HI_OPTION { add_option(HI_OPTION); }
- | HS_OPTION { add_option(HS_OPTION); }
- | EQU_OPTION { add_option(EQU_OPTION); }
- | NEU_OPTION { add_option(NEU_OPTION); }
- | LTU_OPTION { add_option(LTU_OPTION); }
- | LEU_OPTION { add_option(LEU_OPTION); }
- | GTU_OPTION { add_option(GTU_OPTION); }
- | GEU_OPTION { add_option(GEU_OPTION); }
- | NUM_OPTION { add_option(NUM_OPTION); }
- | NAN_OPTION { add_option(NAN_OPTION); }
+compare_spec:EQ_OPTION { recognizer->add_option(EQ_OPTION); }
+ | NE_OPTION { recognizer->add_option(NE_OPTION); }
+ | LT_OPTION { recognizer->add_option(LT_OPTION); }
+ | LE_OPTION { recognizer->add_option(LE_OPTION); }
+ | GT_OPTION { recognizer->add_option(GT_OPTION); }
+ | GE_OPTION { recognizer->add_option(GE_OPTION); }
+ | LO_OPTION { recognizer->add_option(LO_OPTION); }
+ | LS_OPTION { recognizer->add_option(LS_OPTION); }
+ | HI_OPTION { recognizer->add_option(HI_OPTION); }
+ | HS_OPTION { recognizer->add_option(HS_OPTION); }
+ | EQU_OPTION { recognizer->add_option(EQU_OPTION); }
+ | NEU_OPTION { recognizer->add_option(NEU_OPTION); }
+ | LTU_OPTION { recognizer->add_option(LTU_OPTION); }
+ | LEU_OPTION { recognizer->add_option(LEU_OPTION); }
+ | GTU_OPTION { recognizer->add_option(GTU_OPTION); }
+ | GEU_OPTION { recognizer->add_option(GEU_OPTION); }
+ | NUM_OPTION { recognizer->add_option(NUM_OPTION); }
+ | NAN_OPTION { recognizer->add_option(NAN_OPTION); }
;
-prmt_spec: PRMT_F4E_MODE { add_option( PRMT_F4E_MODE); }
- | PRMT_B4E_MODE { add_option( PRMT_B4E_MODE); }
- | PRMT_RC8_MODE { add_option( PRMT_RC8_MODE); }
- | PRMT_RC16_MODE{ add_option( PRMT_RC16_MODE);}
- | PRMT_ECL_MODE { add_option( PRMT_ECL_MODE); }
- | PRMT_ECR_MODE { add_option( PRMT_ECR_MODE); }
+prmt_spec: PRMT_F4E_MODE { recognizer->add_option( PRMT_F4E_MODE); }
+ | PRMT_B4E_MODE { recognizer->add_option( PRMT_B4E_MODE); }
+ | PRMT_RC8_MODE { recognizer->add_option( PRMT_RC8_MODE); }
+ | PRMT_RC16_MODE{ recognizer->add_option( PRMT_RC16_MODE);}
+ | PRMT_ECL_MODE { recognizer->add_option( PRMT_ECL_MODE); }
+ | PRMT_ECR_MODE { recognizer->add_option( PRMT_ECR_MODE); }
;
-wmma_spec: WMMA_DIRECTIVE LAYOUT CONFIGURATION{add_space_spec(global_space,0);add_ptr_spec(global_space); add_wmma_option($1);add_wmma_option($2);add_wmma_option($3);}
- | WMMA_DIRECTIVE LAYOUT LAYOUT CONFIGURATION{add_wmma_option($1);add_wmma_option($2);add_wmma_option($3);add_wmma_option($4);}
+wmma_spec: WMMA_DIRECTIVE LAYOUT CONFIGURATION{recognizer->add_space_spec(global_space,0);recognizer->add_ptr_spec(global_space); recognizer->add_wmma_option($1);recognizer->add_wmma_option($2);recognizer->add_wmma_option($3);}
+ | WMMA_DIRECTIVE LAYOUT LAYOUT CONFIGURATION{recognizer->add_wmma_option($1);recognizer->add_wmma_option($2);recognizer->add_wmma_option($3);recognizer->add_wmma_option($4);}
;
-vp_spec: WMMA_DIRECTIVE LAYOUT CONFIGURATION{add_space_spec(global_space,0);add_ptr_spec(global_space);add_wmma_option($1);add_wmma_option($2);add_wmma_option($3);}
- | WMMA_DIRECTIVE LAYOUT LAYOUT CONFIGURATION{add_wmma_option($1);add_wmma_option($2);add_wmma_option($3);add_wmma_option($4);}
+vp_spec: WMMA_DIRECTIVE LAYOUT CONFIGURATION{recognizer->add_space_spec(global_space,0);recognizer->add_ptr_spec(global_space);recognizer->add_wmma_option($1);recognizer->add_wmma_option($2);recognizer->add_wmma_option($3);}
+ | WMMA_DIRECTIVE LAYOUT LAYOUT CONFIGURATION{recognizer->add_wmma_option($1);recognizer->add_wmma_option($2);recognizer->add_wmma_option($3);recognizer->add_wmma_option($4);}
;
@@ -550,80 +561,77 @@ vp_spec: WMMA_DIRECTIVE LAYOUT CONFIGURATION{add_space_spec(global_space,0);add_
operand_list: operand
| operand COMMA operand_list;
-operand: IDENTIFIER { add_scalar_operand( $1 ); }
- | EXCLAMATION IDENTIFIER { add_neg_pred_operand( $2 ); }
- | MINUS IDENTIFIER { add_scalar_operand( $2 ); change_operand_neg(); }
+operand: IDENTIFIER { recognizer->add_scalar_operand( $1 ); }
+ | EXCLAMATION IDENTIFIER { recognizer->add_neg_pred_operand( $2 ); }
+ | MINUS IDENTIFIER { recognizer->add_scalar_operand( $2 ); recognizer->change_operand_neg(); }
| memory_operand
| literal_operand
| builtin_operand
| vector_operand
- | MINUS vector_operand { change_operand_neg(); }
+ | MINUS vector_operand { recognizer->change_operand_neg(); }
| tex_operand
- | IDENTIFIER PLUS INT_OPERAND { add_address_operand($1,$3); }
- | IDENTIFIER LO_OPTION { add_scalar_operand( $1 ); change_operand_lohi(1);}
- | MINUS IDENTIFIER LO_OPTION { add_scalar_operand( $2 ); change_operand_lohi(1); change_operand_neg();}
- | IDENTIFIER HI_OPTION { add_scalar_operand( $1 ); change_operand_lohi(2);}
- | MINUS IDENTIFIER HI_OPTION { add_scalar_operand( $2 ); change_operand_lohi(2); change_operand_neg();}
- | IDENTIFIER PIPE IDENTIFIER { add_2vector_operand($1,$3); change_double_operand_type(-1);}
- | IDENTIFIER PIPE IDENTIFIER LO_OPTION { add_2vector_operand($1,$3); change_double_operand_type(-1); change_operand_lohi(1);}
- | IDENTIFIER PIPE IDENTIFIER HI_OPTION { add_2vector_operand($1,$3); change_double_operand_type(-1); change_operand_lohi(2);}
- | IDENTIFIER BACKSLASH IDENTIFIER { add_2vector_operand($1,$3); change_double_operand_type(-3);}
- | IDENTIFIER BACKSLASH IDENTIFIER LO_OPTION { add_2vector_operand($1,$3); change_double_operand_type(-3); change_operand_lohi(1);}
- | IDENTIFIER BACKSLASH IDENTIFIER HI_OPTION { add_2vector_operand($1,$3); change_double_operand_type(-3); change_operand_lohi(2);}
+ | IDENTIFIER PLUS INT_OPERAND { recognizer->add_address_operand($1,$3); }
+ | IDENTIFIER LO_OPTION { recognizer->add_scalar_operand( $1 ); recognizer->change_operand_lohi(1);}
+ | MINUS IDENTIFIER LO_OPTION { recognizer->add_scalar_operand( $2 ); recognizer->change_operand_lohi(1); recognizer->change_operand_neg();}
+ | IDENTIFIER HI_OPTION { recognizer->add_scalar_operand( $1 ); recognizer->change_operand_lohi(2);}
+ | MINUS IDENTIFIER HI_OPTION { recognizer->add_scalar_operand( $2 ); recognizer->change_operand_lohi(2); recognizer->change_operand_neg();}
+ | IDENTIFIER PIPE IDENTIFIER { recognizer->add_2vector_operand($1,$3); recognizer->change_double_operand_type(-1);}
+ | IDENTIFIER PIPE IDENTIFIER LO_OPTION { recognizer->add_2vector_operand($1,$3); recognizer->change_double_operand_type(-1); recognizer->change_operand_lohi(1);}
+ | IDENTIFIER PIPE IDENTIFIER HI_OPTION { recognizer->add_2vector_operand($1,$3); recognizer->change_double_operand_type(-1); recognizer->change_operand_lohi(2);}
+ | IDENTIFIER BACKSLASH IDENTIFIER { recognizer->add_2vector_operand($1,$3); recognizer->change_double_operand_type(-3);}
+ | IDENTIFIER BACKSLASH IDENTIFIER LO_OPTION { recognizer->add_2vector_operand($1,$3); recognizer->change_double_operand_type(-3); recognizer->change_operand_lohi(1);}
+ | IDENTIFIER BACKSLASH IDENTIFIER HI_OPTION { recognizer->add_2vector_operand($1,$3); recognizer->change_double_operand_type(-3); recognizer->change_operand_lohi(2);}
;
-vector_operand: LEFT_BRACE IDENTIFIER COMMA IDENTIFIER RIGHT_BRACE { add_2vector_operand($2,$4); }
- | LEFT_BRACE IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER RIGHT_BRACE { add_3vector_operand($2,$4,$6); }
- | LEFT_BRACE IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER RIGHT_BRACE { add_4vector_operand($2,$4,$6,$8); }
- | LEFT_BRACE IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER RIGHT_BRACE { add_8vector_operand($2,$4,$6,$8,$10,$12,$14,$16); }
- | LEFT_BRACE IDENTIFIER RIGHT_BRACE { add_1vector_operand($2); }
+vector_operand: LEFT_BRACE IDENTIFIER COMMA IDENTIFIER RIGHT_BRACE { recognizer->add_2vector_operand($2,$4); }
+ | LEFT_BRACE IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER RIGHT_BRACE { recognizer->add_3vector_operand($2,$4,$6); }
+ | LEFT_BRACE IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER RIGHT_BRACE { recognizer->add_4vector_operand($2,$4,$6,$8); }
+ | LEFT_BRACE IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER COMMA IDENTIFIER RIGHT_BRACE { recognizer->add_8vector_operand($2,$4,$6,$8,$10,$12,$14,$16); }
+ | LEFT_BRACE IDENTIFIER RIGHT_BRACE { recognizer->add_1vector_operand($2); }
;
-tex_operand: LEFT_SQUARE_BRACKET IDENTIFIER COMMA { add_scalar_operand($2); }
+tex_operand: LEFT_SQUARE_BRACKET IDENTIFIER COMMA { recognizer->add_scalar_operand($2); }
vector_operand
RIGHT_SQUARE_BRACKET
;
-builtin_operand: SPECIAL_REGISTER DIMENSION_MODIFIER { add_builtin_operand($1,$2); }
- | SPECIAL_REGISTER { add_builtin_operand($1,-1); }
+builtin_operand: SPECIAL_REGISTER DIMENSION_MODIFIER { recognizer->add_builtin_operand($1,$2); }
+ | SPECIAL_REGISTER { recognizer->add_builtin_operand($1,-1); }
;
-memory_operand : LEFT_SQUARE_BRACKET address_expression RIGHT_SQUARE_BRACKET { add_memory_operand(); }
- | IDENTIFIER LEFT_SQUARE_BRACKET address_expression RIGHT_SQUARE_BRACKET { add_memory_operand(); change_memory_addr_space($1); }
- | IDENTIFIER LEFT_SQUARE_BRACKET literal_operand RIGHT_SQUARE_BRACKET { change_memory_addr_space($1); }
- | IDENTIFIER LEFT_SQUARE_BRACKET twin_operand RIGHT_SQUARE_BRACKET { change_memory_addr_space($1); add_memory_operand();}
- | MINUS memory_operand { change_operand_neg(); }
+memory_operand : LEFT_SQUARE_BRACKET address_expression RIGHT_SQUARE_BRACKET { recognizer->add_memory_operand(); }
+ | IDENTIFIER LEFT_SQUARE_BRACKET address_expression RIGHT_SQUARE_BRACKET { recognizer->add_memory_operand(); recognizer->change_memory_addr_space($1); }
+ | IDENTIFIER LEFT_SQUARE_BRACKET literal_operand RIGHT_SQUARE_BRACKET { recognizer->change_memory_addr_space($1); }
+ | IDENTIFIER LEFT_SQUARE_BRACKET twin_operand RIGHT_SQUARE_BRACKET { recognizer->change_memory_addr_space($1); recognizer->add_memory_operand();}
+ | MINUS memory_operand { recognizer->change_operand_neg(); }
;
-twin_operand : IDENTIFIER PLUS IDENTIFIER { add_double_operand($1,$3); change_double_operand_type(1); }
- | IDENTIFIER PLUS IDENTIFIER LO_OPTION { add_double_operand($1,$3); change_double_operand_type(1); change_operand_lohi(1); }
- | IDENTIFIER PLUS IDENTIFIER HI_OPTION { add_double_operand($1,$3); change_double_operand_type(1); change_operand_lohi(2); }
- | IDENTIFIER PLUS EQUALS IDENTIFIER { add_double_operand($1,$4); change_double_operand_type(2); }
- | IDENTIFIER PLUS EQUALS IDENTIFIER LO_OPTION { add_double_operand($1,$4); change_double_operand_type(2); change_operand_lohi(1); }
- | IDENTIFIER PLUS EQUALS IDENTIFIER HI_OPTION { add_double_operand($1,$4); change_double_operand_type(2); change_operand_lohi(2); }
- | IDENTIFIER PLUS EQUALS INT_OPERAND { add_address_operand($1,$4); change_double_operand_type(3); }
+twin_operand : IDENTIFIER PLUS IDENTIFIER { recognizer->add_double_operand($1,$3); recognizer->change_double_operand_type(1); }
+ | IDENTIFIER PLUS IDENTIFIER LO_OPTION { recognizer->add_double_operand($1,$3); recognizer->change_double_operand_type(1); recognizer->change_operand_lohi(1); }
+ | IDENTIFIER PLUS IDENTIFIER HI_OPTION { recognizer->add_double_operand($1,$3); recognizer->change_double_operand_type(1); recognizer->change_operand_lohi(2); }
+ | IDENTIFIER PLUS EQUALS IDENTIFIER { recognizer->add_double_operand($1,$4); recognizer->change_double_operand_type(2); }
+ | IDENTIFIER PLUS EQUALS IDENTIFIER LO_OPTION { recognizer->add_double_operand($1,$4); recognizer->change_double_operand_type(2); recognizer->change_operand_lohi(1); }
+ | IDENTIFIER PLUS EQUALS IDENTIFIER HI_OPTION { recognizer->add_double_operand($1,$4); recognizer->change_double_operand_type(2); recognizer->change_operand_lohi(2); }
+ | IDENTIFIER PLUS EQUALS INT_OPERAND { recognizer->add_address_operand($1,$4); recognizer->change_double_operand_type(3); }
;
-literal_operand : INT_OPERAND { add_literal_int($1); }
- | FLOAT_OPERAND { add_literal_float($1); }
- | DOUBLE_OPERAND { add_literal_double($1); }
+literal_operand : INT_OPERAND { recognizer->add_literal_int($1); }
+ | FLOAT_OPERAND { recognizer->add_literal_float($1); }
+ | DOUBLE_OPERAND { recognizer->add_literal_double($1); }
;
-address_expression: IDENTIFIER { add_address_operand($1,0); }
- | IDENTIFIER LO_OPTION { add_address_operand($1,0); change_operand_lohi(1);}
- | IDENTIFIER HI_OPTION { add_address_operand($1,0); change_operand_lohi(2); }
- | IDENTIFIER PLUS INT_OPERAND { add_address_operand($1,$3); }
- | INT_OPERAND { add_address_operand2($1); }
+address_expression: IDENTIFIER { recognizer->add_address_operand($1,0); }
+ | IDENTIFIER LO_OPTION { recognizer->add_address_operand($1,0); recognizer->change_operand_lohi(1);}
+ | IDENTIFIER HI_OPTION { recognizer->add_address_operand($1,0); recognizer->change_operand_lohi(2); }
+ | IDENTIFIER PLUS INT_OPERAND { recognizer->add_address_operand($1,$3); }
+ | INT_OPERAND { recognizer->add_address_operand2($1); }
;
%%
-extern int ptx_lineno;
-extern const char *g_filename;
-
-void syntax_not_implemented()
+void syntax_not_implemented(yyscan_t yyscanner, ptx_recognizer* recognizer)
{
- printf("Parse error (%s:%u): this syntax is not (yet) implemented:\n",g_filename,ptx_lineno);
- ptx_error(NULL);
+ printf("Parse error (%s): this syntax is not (yet) implemented:\n", recognizer->gpgpu_ctx->g_filename);
+ ptx_error(yyscanner, recognizer, NULL);
abort();
}
diff --git a/src/cuda-sim/ptx_ir.cc b/src/cuda-sim/ptx_ir.cc
index e4e0c09..6978cc1 100644
--- a/src/cuda-sim/ptx_ir.cc
+++ b/src/cuda-sim/ptx_ir.cc
@@ -28,6 +28,7 @@
#include "ptx_parser.h"
#include "ptx_ir.h"
+typedef void * yyscan_t;
#include "ptx.tab.h"
#include "opcodes.h"
#include <stdio.h>
@@ -38,14 +39,21 @@
#include "assert.h"
#include "cuda-sim.h"
+#include "../../libcuda/gpgpu_context.h"
#define STR_SIZE 1024
-unsigned symbol::sm_next_uid = 1;
+const ptx_instruction* gpgpu_context::pc_to_instruction(unsigned pc)
+{
+ if( pc < s_g_pc_to_insn.size() )
+ return s_g_pc_to_insn[pc];
+ else
+ return NULL;
+}
unsigned symbol::get_uid()
{
- unsigned result = sm_next_uid++;
+ unsigned result = (gpgpu_ctx->symbol_sm_next_uid)++;
return result;
}
@@ -82,8 +90,9 @@ symbol_table::symbol_table()
assert(0);
}
-symbol_table::symbol_table( const char *scope_name, unsigned entry_point, symbol_table *parent )
+symbol_table::symbol_table( const char *scope_name, unsigned entry_point, symbol_table *parent, gpgpu_context* ctx )
{
+ gpgpu_ctx = ctx;
m_scope_name = std::string(scope_name);
m_reg_allocator=0;
m_shared_next = 0;
@@ -149,7 +158,7 @@ symbol *symbol_table::add_variable( const char *identifier, const type_info *typ
std::string key(identifier);
assert( m_symbols.find(key) == m_symbols.end() );
snprintf(buf,1024,"%s:%u",filename,line);
- symbol *s = new symbol(identifier,type,buf,size);
+ symbol *s = new symbol(identifier,type,buf,size,gpgpu_ctx);
m_symbols[ key ] = s;
if ( type != NULL && type->get_key().is_global() ) {
@@ -170,7 +179,7 @@ void symbol_table::add_function( function_info *func, const char *filename, unsi
char buf[1024];
snprintf(buf,1024,"%s:%u",filename,linenumber);
type_info *type = add_type( func );
- symbol *s = new symbol(func->get_name().c_str(),type,buf,0);
+ symbol *s = new symbol(func->get_name().c_str(),type,buf,0,gpgpu_ctx);
s->set_function(func);
m_symbols[ func->get_name() ] = s;
}
@@ -182,7 +191,7 @@ symbol_table* symbol_table::start_inst_group() {
//previous added
assert(m_inst_group_symtab.find(std::string(inst_group_name)) == m_inst_group_symtab.end());
- symbol_table *sym_table = new symbol_table(inst_group_name, 3/*inst group*/, this );
+ symbol_table *sym_table = new symbol_table(inst_group_name, 3/*inst group*/, this, gpgpu_ctx );
sym_table->m_global_next = m_global_next;
sym_table->m_shared_next = m_shared_next;
@@ -220,7 +229,7 @@ bool symbol_table::add_function_decl( const char *name, int entry_point, functio
*func_info = m_function_info_lookup[key];
prior_decl = true;
} else {
- *func_info = new function_info(entry_point);
+ *func_info = new function_info(entry_point, gpgpu_ctx);
(*func_info)->set_name(name);
(*func_info)->set_maxnt_id(0);
m_function_info_lookup[key] = *func_info;
@@ -231,7 +240,7 @@ bool symbol_table::add_function_decl( const char *name, int entry_point, functio
*sym_table = m_function_symtab_lookup[key];
} else {
assert( !prior_decl );
- *sym_table = new symbol_table( "", entry_point, this );
+ *sym_table = new symbol_table( "", entry_point, this, gpgpu_ctx );
// Initial setup code to support a register represented as "_".
// This register is used when an instruction operand is
@@ -320,11 +329,9 @@ void symbol_table::dump()
printf("\n");
}
-unsigned operand_info::sm_next_uid=1;
-
unsigned operand_info::get_uid()
{
- unsigned result = sm_next_uid++;
+ unsigned result = (gpgpu_ctx->operand_info_sm_next_uid)++;
return result;
}
@@ -1013,7 +1020,7 @@ void copy_buffer_to_frame(ptx_thread_info * thread, const arg_buffer_t &a)
{
if( a.is_reg() ) {
ptx_reg_t value = a.get_reg();
- operand_info dst_reg = operand_info(a.get_dst());
+ operand_info dst_reg = operand_info(a.get_dst(), thread->get_gpu()->gpgpu_ctx);
thread->set_reg(dst_reg.get_symbol(),value);
} else {
const void *buffer = a.get_param_buffer();
@@ -1037,7 +1044,8 @@ void copy_buffer_list_into_frame(ptx_thread_info * thread, arg_buffer_list_t &ar
static std::list<operand_info> check_operands( int opcode,
const std::list<int> &scalar_type,
- const std::list<operand_info> &operands )
+ const std::list<operand_info> &operands,
+ gpgpu_context* ctx)
{
static int g_warn_literal_operands_two_type_inst;
if( (opcode == CVT_OP) || (opcode == SET_OP) || (opcode == SLCT_OP) || (opcode == TEX_OP) || (opcode==MMA_OP) || (opcode == DP4A_OP)) {
@@ -1064,7 +1072,7 @@ static std::list<operand_info> check_operands( int opcode,
if( (op.get_type() == double_op_t) && (inst_type == F32_TYPE) ) {
ptx_reg_t v = op.get_literal_value();
float u = (float)v.f64;
- operand_info n(u);
+ operand_info n(u, ctx);
result.push_back(n);
} else {
result.push_back(op);
@@ -1094,16 +1102,18 @@ ptx_instruction::ptx_instruction( int opcode,
const char *file,
unsigned line,
const char *source,
- const core_config *config ) : warp_inst_t(config)
+ const core_config *config,
+ gpgpu_context* ctx ) : warp_inst_t(config), m_return_var(ctx)
{
- m_uid = ++g_num_ptx_inst_uid;
+ gpgpu_ctx = ctx;
+ m_uid = ++(ctx->g_num_ptx_inst_uid);
m_PC = 0;
m_opcode = opcode;
m_pred = pred;
m_neg_pred = neg_pred;
m_pred_mod = pred_mod;
m_label = label;
- const std::list<operand_info> checked_operands = check_operands(opcode,scalar_type,operands);
+ const std::list<operand_info> checked_operands = check_operands(opcode,scalar_type,operands, ctx);
m_operands.insert(m_operands.begin(), checked_operands.begin(), checked_operands.end() );
m_return_var = return_var;
m_options = options;
@@ -1369,12 +1379,16 @@ std::string ptx_instruction::to_string() const
m_source.c_str() );
return std::string( buf );
}
+operand_info ptx_instruction::get_pred() const
+{
+ return operand_info( m_pred, gpgpu_ctx);
+}
-unsigned function_info::sm_next_uid = 1;
-function_info::function_info(int entry_point )
+function_info::function_info(int entry_point, gpgpu_context* ctx )
{
- m_uid = sm_next_uid++;
+ gpgpu_ctx = ctx;
+ m_uid = (gpgpu_ctx->function_info_sm_next_uid)++;
m_entry_point = (entry_point==1)?true:false;
m_extern = (entry_point==2)?true:false;
num_reconvergence_pairs = 0;
diff --git a/src/cuda-sim/ptx_ir.h b/src/cuda-sim/ptx_ir.h
index 1af85de..f4c5c37 100644
--- a/src/cuda-sim/ptx_ir.h
+++ b/src/cuda-sim/ptx_ir.h
@@ -43,6 +43,8 @@
#include "memory.h"
+class gpgpu_context;
+
class type_info_key {
public:
type_info_key()
@@ -150,8 +152,9 @@ class operand_info;
class symbol {
public:
- symbol( const char *name, const type_info *type, const char *location, unsigned size )
+ symbol( const char *name, const type_info *type, const char *location, unsigned size, gpgpu_context* ctx )
{
+ gpgpu_ctx = ctx;
m_uid = get_uid();
m_name = name;
m_decl_location = location;
@@ -271,6 +274,7 @@ public:
unsigned uid() const { return m_uid; }
private:
+ gpgpu_context* gpgpu_ctx;
unsigned get_uid();
unsigned m_uid;
const type_info *m_type;
@@ -297,14 +301,12 @@ private:
bool m_reg_num_valid;
std::list<operand_info> m_initializer;
- static unsigned sm_next_uid;
-
};
class symbol_table {
public:
symbol_table();
- symbol_table( const char *scope_name, unsigned entry_point, symbol_table *parent );
+ symbol_table( const char *scope_name, unsigned entry_point, symbol_table *parent, gpgpu_context* ctx);
void set_name( const char *name );
const ptx_version &get_ptx_version() const;
unsigned get_sm_target() const;
@@ -346,6 +348,9 @@ public:
symbol_table* start_inst_group();
symbol_table* end_inst_group();
+ // backward pointer
+ class gpgpu_context* gpgpu_ctx;
+
private:
unsigned m_reg_allocator;
unsigned m_shared_next;
@@ -372,9 +377,9 @@ private:
class operand_info {
public:
- operand_info()
+ operand_info(gpgpu_context* ctx)
{
- init();
+ init(ctx);
m_is_non_arch_reg = false;
m_addr_space = undefined_space;
m_operand_lohi = 0;
@@ -387,9 +392,9 @@ public:
m_addr_offset = 0;
m_value.m_symbolic=NULL;
}
- operand_info( const symbol *addr )
+ operand_info( const symbol *addr, gpgpu_context* ctx )
{
- init();
+ init(ctx);
m_is_non_arch_reg = false;
m_addr_space = undefined_space;
m_operand_lohi = 0;
@@ -430,9 +435,9 @@ public:
m_is_return_var = false;
m_immediate_address=false;
}
- operand_info( const symbol *addr1, const symbol *addr2 )
+ operand_info( const symbol *addr1, const symbol *addr2, gpgpu_context* ctx )
{
- init();
+ init(ctx);
m_is_non_arch_reg = false;
m_addr_space = undefined_space;
m_operand_lohi = 0;
@@ -457,9 +462,9 @@ public:
m_is_return_var = false;
m_immediate_address=false;
}
- operand_info( int builtin_id, int dim_mod )
+ operand_info( int builtin_id, int dim_mod, gpgpu_context* ctx )
{
- init();
+ init(ctx);
m_is_non_arch_reg = false;
m_addr_space = undefined_space;
m_operand_lohi = 0;
@@ -476,9 +481,9 @@ public:
m_is_return_var = false;
m_immediate_address=false;
}
- operand_info( const symbol *addr, int offset )
+ operand_info( const symbol *addr, int offset, gpgpu_context* ctx )
{
- init();
+ init(ctx);
m_is_non_arch_reg = false;
m_addr_space = undefined_space;
m_operand_lohi = 0;
@@ -495,9 +500,9 @@ public:
m_is_return_var = false;
m_immediate_address=false;
}
- operand_info( unsigned x )
+ operand_info( unsigned x, gpgpu_context* ctx )
{
- init();
+ init(ctx);
m_is_non_arch_reg = false;
m_addr_space = undefined_space;
m_operand_lohi = 0;
@@ -514,9 +519,9 @@ public:
m_is_return_var = false;
m_immediate_address=true;
}
- operand_info( int x )
+ operand_info( int x, gpgpu_context* ctx )
{
- init();
+ init(ctx);
m_is_non_arch_reg = false;
m_addr_space = undefined_space;
m_operand_lohi = 0;
@@ -533,9 +538,9 @@ public:
m_is_return_var = false;
m_immediate_address=false;
}
- operand_info( float x )
+ operand_info( float x, gpgpu_context* ctx )
{
- init();
+ init(ctx);
m_is_non_arch_reg = false;
m_addr_space = undefined_space;
m_operand_lohi = 0;
@@ -552,9 +557,9 @@ public:
m_is_return_var = false;
m_immediate_address=false;
}
- operand_info( double x )
+ operand_info( double x, gpgpu_context* ctx )
{
- init();
+ init(ctx);
m_is_non_arch_reg = false;
m_addr_space = undefined_space;
m_operand_lohi = 0;
@@ -571,9 +576,9 @@ public:
m_is_return_var = false;
m_immediate_address=false;
}
- operand_info( const symbol *s1, const symbol *s2, const symbol *s3, const symbol *s4 )
+ operand_info( const symbol *s1, const symbol *s2, const symbol *s3, const symbol *s4, gpgpu_context* ctx )
{
- init();
+ init(ctx);
m_is_non_arch_reg = false;
m_addr_space = undefined_space;
m_operand_lohi = 0;
@@ -598,9 +603,9 @@ public:
m_is_return_var = false;
m_immediate_address=false;
}
- operand_info( const symbol *s1, const symbol *s2, const symbol *s3, const symbol *s4 ,const symbol *s5,const symbol *s6,const symbol *s7, const symbol *s8)
+ operand_info( const symbol *s1, const symbol *s2, const symbol *s3, const symbol *s4 ,const symbol *s5,const symbol *s6,const symbol *s7, const symbol *s8, gpgpu_context* ctx)
{
- init();
+ init(ctx);
m_is_non_arch_reg = false;
m_addr_space = undefined_space;
m_operand_lohi = 0;
@@ -626,8 +631,9 @@ public:
m_immediate_address=false;
}
- void init()
+ void init(gpgpu_context* ctx)
{
+ gpgpu_ctx = ctx;
m_uid=(unsigned)-1;
m_valid=false;
m_vector=false;
@@ -837,6 +843,7 @@ public:
bool is_non_arch_reg() const { return m_is_non_arch_reg; }
private:
+ gpgpu_context* gpgpu_ctx;
unsigned m_uid;
bool m_valid;
bool m_vector;
@@ -866,12 +873,10 @@ private:
bool m_is_return_var;
bool m_is_non_arch_reg;
- static unsigned sm_next_uid;
unsigned get_uid();
};
extern const char *g_opcode_string[];
-extern unsigned g_num_ptx_inst_uid;
struct basic_block_t {
basic_block_t( unsigned ID, ptx_instruction *begin, ptx_instruction *end, bool entry, bool ex)
{
@@ -931,7 +936,8 @@ public:
const char *file,
unsigned line,
const char *source,
- const core_config *config );
+ const core_config *config,
+ gpgpu_context* ctx);
void print_insn() const;
virtual void print_insn( FILE *fp ) const;
@@ -951,7 +957,7 @@ public:
unsigned source_line() const { return m_source_line;}
unsigned get_num_operands() const { return m_operands.size();}
bool has_pred() const { return m_pred != NULL;}
- operand_info get_pred() const { return operand_info( m_pred );}
+ operand_info get_pred() const;
bool get_pred_neg() const { return m_neg_pred;}
int get_pred_mod() const { return m_pred_mod;}
const char *get_source() const { return m_source.c_str();}
@@ -1186,7 +1192,8 @@ private:
virtual void pre_decode();
friend class function_info;
- static unsigned g_num_ptx_inst_uid;
+ // backward pointer
+ class gpgpu_context* gpgpu_ctx;
};
class param_info {
@@ -1228,7 +1235,7 @@ private:
class function_info {
public:
- function_info(int entry_point );
+ function_info(int entry_point, gpgpu_context* ctx );
const ptx_version &get_ptx_version() const { return m_symtab->get_ptx_version(); }
unsigned get_sm_target() const { return m_symtab->get_sm_target(); }
bool is_extern() const { return m_extern; }
@@ -1365,13 +1372,6 @@ public:
return m_symtab;
}
- static const ptx_instruction* pc_to_instruction(unsigned pc)
- {
- if( pc < s_g_pc_to_insn.size() )
- return s_g_pc_to_insn[pc];
- else
- return NULL;
- }
unsigned local_mem_framesize() const
{
return m_local_mem_framesize;
@@ -1398,6 +1398,8 @@ public:
void set_maxnt_id(unsigned maxthreads) { maxnt_id = maxthreads;}
unsigned get_maxnt_id() { return maxnt_id;}
+ // backward pointer
+ class gpgpu_context* gpgpu_ctx;
private:
unsigned maxnt_id;
@@ -1427,9 +1429,6 @@ private:
symbol_table *m_symtab;
- static std::vector<ptx_instruction*> s_g_pc_to_insn; // a direct mapping from PC to instruction
- static unsigned sm_next_uid;
-
//parameter size for device kernels
int m_args_aligned_size;
@@ -1438,14 +1437,14 @@ private:
class arg_buffer_t {
public:
- arg_buffer_t()
+ arg_buffer_t(gpgpu_context* ctx) : m_src_op(ctx)
{
m_is_reg=false;
m_is_param=false;
m_param_value=NULL;
m_reg_value=ptx_reg_t();
}
- arg_buffer_t( const arg_buffer_t &another )
+ arg_buffer_t( const arg_buffer_t &another, gpgpu_context* ctx ) : m_src_op(ctx)
{
make_copy(another);
}
@@ -1575,11 +1574,8 @@ struct textureInfo {
extern std::map<std::string,symbol_table*> g_sym_name_to_symbol_table;
-extern bool g_keep_intermediate_files;
-
void gpgpu_ptx_assemble( std::string kname, void *kinfo );
#include "../option_parser.h"
-void ptx_reg_options(option_parser_t opp);
unsigned ptx_kernel_shmem_size( void *kernel_impl );
unsigned ptx_kernel_nregs( void *kernel_impl );
diff --git a/src/cuda-sim/ptx_loader.cc b/src/cuda-sim/ptx_loader.cc
index 8c6f361..dca3cec 100644
--- a/src/cuda-sim/ptx_loader.cc
+++ b/src/cuda-sim/ptx_loader.cc
@@ -33,44 +33,40 @@
#include <dirent.h>
#include <fstream>
#include <sstream>
-
-/// globals
-
-memory_space *g_global_mem;
-memory_space *g_tex_mem;
-memory_space *g_surf_mem;
-memory_space *g_param_mem;
-bool g_override_embedded_ptx = false;
+#include "../../libcuda/gpgpu_context.h"
/// extern prototypes
-extern int ptx_parse();
-extern int ptx__scan_string(const char*);
+extern int ptx_error( yyscan_t yyscanner, const char *s );
+extern int ptx_lex_init(yyscan_t* scanner);
+extern void ptx_set_in(FILE * _in_str ,yyscan_t yyscanner );
+extern int ptx_parse(yyscan_t scanner, ptx_recognizer* recognizer);
+extern int ptx_lex_destroy(yyscan_t scanner);
+extern int ptx__scan_string(const char*, yyscan_t scanner);
extern std::map<unsigned,const char*> get_duplicate();
-const char *g_ptxinfo_filename;
-extern int ptxinfo_parse();
-extern int ptxinfo_debug;
-extern FILE *ptxinfo_in;
+typedef void * yyscan_t;
+extern int ptxinfo_lex_init(yyscan_t* scanner);
+extern void ptxinfo_set_in (FILE * _in_str ,yyscan_t yyscanner );
+extern int ptxinfo_parse(yyscan_t scanner, ptxinfo_data* ptxinfo);
+extern int ptxinfo_lex_destroy(yyscan_t scanner);
static bool g_save_embedded_ptx;
static int g_occupancy_sm_number;
-bool g_keep_intermediate_files;
-bool m_ptx_save_converted_ptxplus;
-bool keep_intermediate_files() {return g_keep_intermediate_files;}
+bool ptxinfo_data::keep_intermediate_files() {return g_keep_intermediate_files;}
-void ptx_reg_options(option_parser_t opp)
+void gpgpu_context::ptx_reg_options(option_parser_t opp)
{
option_parser_register(opp, "-save_embedded_ptx", OPT_BOOL, &g_save_embedded_ptx,
"saves ptx files embedded in binary as <n>.ptx",
"0");
- option_parser_register(opp, "-keep", OPT_BOOL, &g_keep_intermediate_files,
+ option_parser_register(opp, "-keep", OPT_BOOL, &(ptxinfo->g_keep_intermediate_files),
"keep intermediate files created by GPGPU-Sim when interfacing with external programs",
"0");
option_parser_register(opp, "-gpgpu_ptx_save_converted_ptxplus", OPT_BOOL,
- &m_ptx_save_converted_ptxplus,
+ &(ptxinfo->m_ptx_save_converted_ptxplus),
"Saved converted ptxplus to a file",
"0");
option_parser_register(opp, "-gpgpu_occupancy_sm_number", OPT_INT32, &g_occupancy_sm_number,
@@ -79,7 +75,7 @@ void ptx_reg_options(option_parser_t opp)
"0");
}
-void print_ptx_file( const char *p, unsigned source_num, const char *filename )
+void gpgpu_context::print_ptx_file( const char *p, unsigned source_num, const char *filename )
{
printf("\nGPGPU-Sim PTX: file _%u.ptx contents:\n\n", source_num );
char *s = strdup(p);
@@ -90,7 +86,7 @@ void print_ptx_file( const char *p, unsigned source_num, const char *filename )
while ( (*u != '\n') && (*u != '\0') ) u++;
unsigned last = (*u == '\0');
*u = '\0';
- const ptx_instruction *pI = ptx_instruction_lookup(filename,n);
+ const ptx_instruction *pI = ptx_parser->ptx_instruction_lookup(filename,n);
char pc[64];
if( pI && pI->get_PC() )
snprintf(pc,64,"%4u", pI->get_PC() );
@@ -105,7 +101,7 @@ void print_ptx_file( const char *p, unsigned source_num, const char *filename )
fflush(stdout);
}
-char* gpgpu_ptx_sim_convert_ptx_and_sass_to_ptxplus(const std::string ptxfilename, const std::string elffilename, const std::string sassfilename)
+char* ptxinfo_data::gpgpu_ptx_sim_convert_ptx_and_sass_to_ptxplus(const std::string ptxfilename, const std::string elffilename, const std::string sassfilename)
{
printf("GPGPU-Sim PTX: converting EMBEDDED .ptx file to ptxplus \n");
@@ -158,7 +154,7 @@ char* gpgpu_ptx_sim_convert_ptx_and_sass_to_ptxplus(const std::string ptxfilenam
}
-symbol_table *gpgpu_ptx_sim_load_ptx_from_string( const char *p, unsigned source_num )
+symbol_table *gpgpu_context::gpgpu_ptx_sim_load_ptx_from_string( const char *p, unsigned source_num )
{
char buf[1024];
snprintf(buf,1024,"_%u.ptx", source_num );
@@ -168,8 +164,9 @@ symbol_table *gpgpu_ptx_sim_load_ptx_from_string( const char *p, unsigned source
fclose(fp);
}
symbol_table *symtab=init_parser(buf);
- ptx__scan_string(p);
- int errors = ptx_parse ();
+ ptx_lex_init(&(ptx_parser->scanner));
+ ptx__scan_string(p, ptx_parser->scanner);
+ int errors = ptx_parse (ptx_parser->scanner, ptx_parser);
if ( errors ) {
char fname[1024];
snprintf(fname,1024,"_ptx_errors_XXXXXX");
@@ -182,6 +179,7 @@ symbol_table *gpgpu_ptx_sim_load_ptx_from_string( const char *p, unsigned source
abort();
exit(40);
}
+ ptx_lex_destroy(ptx_parser->scanner);
if ( g_debug_execution >= 100 )
print_ptx_file(p,source_num,buf);
@@ -190,7 +188,7 @@ symbol_table *gpgpu_ptx_sim_load_ptx_from_string( const char *p, unsigned source
return symtab;
}
-symbol_table *gpgpu_ptx_sim_load_ptx_from_filename( const char *filename )
+symbol_table *gpgpu_context::gpgpu_ptx_sim_load_ptx_from_filename( const char *filename )
{
symbol_table *symtab=init_parser(filename);
printf("GPGPU-Sim PTX: finished parsing EMBEDDED .ptx file %s\n",filename);
@@ -327,13 +325,12 @@ char* get_app_binary_name(){
return self_exe_path;
}
-void gpgpu_ptx_info_load_from_filename( const char *filename, unsigned sm_version)
+void gpgpu_context::gpgpu_ptx_info_load_from_filename( const char *filename, unsigned sm_version)
{
std::string ptxas_filename(std::string(filename) + "as");
char buff[1024], extra_flags[1024];
extra_flags[0]=0;
- extern bool g_cdp_enabled;
- if(!g_cdp_enabled)
+ if(!device_runtime->g_cdp_enabled)
snprintf(extra_flags,1024,"--gpu-name=sm_%u",sm_version);
else
snprintf(extra_flags,1024,"--compile-only --gpu-name=sm_%u",sm_version);
@@ -346,13 +343,17 @@ void gpgpu_ptx_info_load_from_filename( const char *filename, unsigned sm_versio
exit(1);
}
- g_ptxinfo_filename = strdup(ptxas_filename.c_str());
- ptxinfo_in = fopen(g_ptxinfo_filename,"r");
- ptxinfo_parse();
+ FILE *ptxinfo_in;
+ ptxinfo->g_ptxinfo_filename = strdup(ptxas_filename.c_str());
+ ptxinfo_in = fopen(ptxinfo->g_ptxinfo_filename,"r");
+ ptxinfo_lex_init(&(ptxinfo->scanner));
+ ptxinfo_set_in(ptxinfo_in, ptxinfo->scanner);
+ ptxinfo_parse(ptxinfo->scanner, ptxinfo);
+ ptxinfo_lex_destroy(ptxinfo->scanner);
fclose(ptxinfo_in);
}
-void gpgpu_ptxinfo_load_from_string( const char *p_for_info, unsigned source_num, unsigned sm_version )
+void gpgpu_context::gpgpu_ptxinfo_load_from_string( const char *p_for_info, unsigned source_num, unsigned sm_version, int no_of_ptx )
{
//do ptxas for individual files instead of one big embedded ptx. This prevents the duplicate defs and declarations.
char ptx_file[1000];
@@ -396,8 +397,7 @@ void gpgpu_ptxinfo_load_from_string( const char *p_for_info, unsigned source_num
"A register size/SM mismatch may result in occupancy differences." );
exit(1);
}
- extern bool g_cdp_enabled;
- if(!g_cdp_enabled)
+ if(!device_runtime->g_cdp_enabled)
snprintf(extra_flags,1024,"--gpu-name=sm_%u", g_occupancy_sm_number);
else
snprintf(extra_flags,1024,"--compile-only --gpu-name=sm_%u",g_occupancy_sm_number);
@@ -410,9 +410,14 @@ void gpgpu_ptxinfo_load_from_string( const char *p_for_info, unsigned source_num
if( result != 0 ) {
// 65280 = duplicate errors
if (result == 65280) {
+ FILE *ptxinfo_in;
ptxinfo_in = fopen(tempfile_ptxinfo,"r");
- g_ptxinfo_filename = tempfile_ptxinfo;
- ptxinfo_parse();
+ ptxinfo->g_ptxinfo_filename = tempfile_ptxinfo;
+ ptxinfo_lex_init(&(ptxinfo->scanner));
+ ptxinfo_set_in(ptxinfo_in, ptxinfo->scanner);
+ ptxinfo_parse(ptxinfo->scanner, ptxinfo);
+ ptxinfo_lex_destroy(ptxinfo->scanner);
+ fclose(ptxinfo_in);
fix_duplicate_errors(fname2);
snprintf(commandline,1024,"$CUDA_INSTALL_PATH/bin/ptxas %s -v %s --output-file /dev/null 2> %s",
@@ -460,8 +465,7 @@ void gpgpu_ptxinfo_load_from_string( const char *p_for_info, unsigned source_num
#if CUDART_VERSION >= 3000
if (sm_version == 0) sm_version = 20;
- extern bool g_cdp_enabled;
- if(!g_cdp_enabled)
+ if(!device_runtime->g_cdp_enabled)
snprintf(extra_flags,1024,"--gpu-name=sm_%u",sm_version);
else
snprintf(extra_flags,1024,"--compile-only --gpu-name=sm_%u",sm_version);
@@ -492,12 +496,17 @@ void gpgpu_ptxinfo_load_from_string( const char *p_for_info, unsigned source_num
}
if(no_of_ptx>0)
- g_ptxinfo_filename = final_tempfile_ptxinfo;
+ ptxinfo->g_ptxinfo_filename = final_tempfile_ptxinfo;
else
- g_ptxinfo_filename = tempfile_ptxinfo;
- ptxinfo_in = fopen(g_ptxinfo_filename,"r");
+ ptxinfo->g_ptxinfo_filename = tempfile_ptxinfo;
+ FILE *ptxinfo_in;
+ ptxinfo_in = fopen(ptxinfo->g_ptxinfo_filename,"r");
- ptxinfo_parse();
+ ptxinfo_lex_init(&(ptxinfo->scanner));
+ ptxinfo_set_in(ptxinfo_in, ptxinfo->scanner);
+ ptxinfo_parse(ptxinfo->scanner, ptxinfo);
+ ptxinfo_lex_destroy(ptxinfo->scanner);
+ fclose(ptxinfo_in);
snprintf(commandline,1024,"rm -f *info");
if( system(commandline) != 0 ) {
@@ -515,4 +524,4 @@ void gpgpu_ptxinfo_load_from_string( const char *p_for_info, unsigned source_num
exit(1);
}
}
-} \ No newline at end of file
+}
diff --git a/src/cuda-sim/ptx_loader.h b/src/cuda-sim/ptx_loader.h
index e5df6a9..d8f1cbc 100644
--- a/src/cuda-sim/ptx_loader.h
+++ b/src/cuda-sim/ptx_loader.h
@@ -29,14 +29,24 @@
#define PTX_LOADER_H_INCLUDED
#include <string>
-extern bool g_override_embedded_ptx;
-extern int no_of_ptx; //counter to track number of ptx files to be extracted in an application.
-
-class symbol_table *gpgpu_ptx_sim_load_ptx_from_string( const char *p, unsigned source_num );
-class symbol_table *gpgpu_ptx_sim_load_ptx_from_filename( const char *filename );
-void gpgpu_ptxinfo_load_from_string( const char *p_for_info, unsigned source_num, unsigned sm_version=20 );
-void gpgpu_ptx_info_load_from_filename( const char *filename, unsigned sm_version );
-char* gpgpu_ptx_sim_convert_ptx_and_sass_to_ptxplus(const std::string ptx_str, const std::string sass_str, const std::string elf_str);
-bool keep_intermediate_files();
+#define PTXINFO_LINEBUF_SIZE 1024
+class gpgpu_context;
+typedef void * yyscan_t;
+class ptxinfo_data{
+ public:
+ ptxinfo_data(gpgpu_context* ctx) {
+ gpgpu_ctx = ctx;
+ }
+ yyscan_t scanner;
+ char linebuf[PTXINFO_LINEBUF_SIZE];
+ unsigned col;
+ const char *g_ptxinfo_filename;
+ class gpgpu_context* gpgpu_ctx;
+ bool g_keep_intermediate_files;
+ bool m_ptx_save_converted_ptxplus;
+ void ptxinfo_addinfo();
+ bool keep_intermediate_files();
+ char* gpgpu_ptx_sim_convert_ptx_and_sass_to_ptxplus(const std::string ptx_str, const std::string sass_str, const std::string elf_str);
+};
#endif
diff --git a/src/cuda-sim/ptx_parser.cc b/src/cuda-sim/ptx_parser.cc
index 25758dd..81b70af 100644
--- a/src/cuda-sim/ptx_parser.cc
+++ b/src/cuda-sim/ptx_parser.cc
@@ -27,79 +27,46 @@
#include "ptx_parser.h"
#include "ptx_ir.h"
+#include "../../libcuda/gpgpu_context.h"
+
+typedef void * yyscan_t;
#include "ptx.tab.h"
#include <stdarg.h>
-extern int ptx_error( const char *s );
-extern int ptx_lineno;
-extern int ptx_parse();
-extern FILE *ptx_in;
+extern int ptx_get_lineno (yyscan_t yyscanner );
+extern YYSTYPE* ptx_get_lval (yyscan_t yyscanner );
+extern int ptx_error( yyscan_t yyscanner, const char *s );
+extern int ptx_lex_init(yyscan_t* scanner);
+extern void ptx_set_in(FILE * _in_str ,yyscan_t yyscanner );
+extern FILE *ptx_get_in (yyscan_t yyscanner );
+extern int ptx_parse(yyscan_t scanner, ptx_recognizer* recognizer);
+extern int ptx_lex_destroy(yyscan_t scanner);
-static const struct core_config *g_shader_core_config;
-void set_ptx_warp_size(const struct core_config * warp_size)
+void ptx_recognizer::set_ptx_warp_size(const struct core_config * warp_size)
{
g_shader_core_config=warp_size;
}
-static bool g_debug_ir_generation=false;
-const char *g_filename;
-unsigned g_max_regs_per_thread = 0;
-
-// the program intermediate representation...
-static symbol_table *g_global_allfiles_symbol_table = NULL;
-static symbol_table *g_global_symbol_table = NULL;
-std::map<std::string,symbol_table*> g_sym_name_to_symbol_table;
-static symbol_table *g_current_symbol_table = NULL;
-static std::list<ptx_instruction*> g_instructions;
-static symbol *g_last_symbol = NULL;
-
-int g_error_detected = 0;
-
-// type specifier stuff:
-memory_space_t g_space_spec = undefined_space;
-memory_space_t g_ptr_spec = undefined_space;
-int g_scalar_type_spec = -1;
-int g_vector_spec = -1;
-int g_alignment_spec = -1;
-int g_size = -1;
-int g_extern_spec = 0;
-
-// variable declaration stuff:
-type_info *g_var_type = NULL;
-
-// instruction definition stuff:
-const symbol *g_pred;
-int g_neg_pred;
-int g_pred_mod;
-symbol *g_label;
-int g_opcode = -1;
-std::list<operand_info> g_operands;
-std::list<int> g_options;
-std::list<int> g_wmma_options;
-std::list<int> g_scalar_type;
#define PTX_PARSE_DPRINTF(...) \
if( g_debug_ir_generation ) { \
- printf(" %s:%u => ",g_filename,ptx_lineno); \
+ printf(" %s:%u => ",gpgpu_ctx->g_filename,ptx_get_lineno(scanner)); \
printf(" (%s:%u) ", __FILE__, __LINE__); \
printf(__VA_ARGS__); \
printf("\n"); \
fflush(stdout); \
}
-static unsigned g_entry_func_param_index=0;
-static function_info *g_func_info = NULL;
static std::map<unsigned,std::string> g_ptx_token_decode;
-static operand_info g_return_var;
const char *decode_token( int type )
{
return g_ptx_token_decode[type].c_str();
}
-void read_parser_environment_variables()
+void ptx_recognizer::read_parser_environment_variables()
{
- g_filename = getenv("PTX_SIM_KERNELFILE");
+ gpgpu_ctx->g_filename = getenv("PTX_SIM_KERNELFILE");
char *dbg_level = getenv("PTX_SIM_DEBUG");
if ( dbg_level && strlen(dbg_level) ) {
int debug_execution=0;
@@ -109,7 +76,7 @@ void read_parser_environment_variables()
}
}
-void init_directive_state()
+void ptx_recognizer::init_directive_state()
{
PTX_PARSE_DPRINTF("init_directive_state");
g_space_spec=undefined_space;
@@ -125,7 +92,7 @@ void init_directive_state()
g_last_symbol = NULL;
}
-void init_instruction_state()
+void ptx_recognizer::init_instruction_state()
{
PTX_PARSE_DPRINTF("init_instruction_state");
g_pred = NULL;
@@ -135,21 +102,20 @@ void init_instruction_state()
g_opcode = -1;
g_options.clear();
g_wmma_options.clear();
- g_return_var = operand_info();
+ g_return_var = operand_info(gpgpu_ctx);
init_directive_state();
}
-symbol_table *init_parser( const char *ptx_filename )
+symbol_table * gpgpu_context::init_parser( const char *ptx_filename )
{
g_filename = strdup(ptx_filename);
if (g_global_allfiles_symbol_table == NULL) {
- g_global_allfiles_symbol_table = new symbol_table("global_allfiles", 0, NULL);
- g_global_symbol_table = g_current_symbol_table = g_global_allfiles_symbol_table;
+ g_global_allfiles_symbol_table = new symbol_table("global_allfiles", 0, NULL, this);
+ ptx_parser->g_global_symbol_table = ptx_parser->g_current_symbol_table = g_global_allfiles_symbol_table;
}
/*else {
g_global_symbol_table = g_current_symbol_table = new symbol_table("global",0,g_global_allfiles_symbol_table);
}*/
- ptx_lineno = 1;
#define DEF(X,Y) g_ptx_token_decode[X] = Y;
#include "ptx_parser_decode.def"
@@ -169,18 +135,22 @@ symbol_table *init_parser( const char *ptx_filename )
g_ptx_token_decode[generic_space] = "generic_space";
g_ptx_token_decode[instruction_space] = "instruction_space";
- init_directive_state();
- init_instruction_state();
+ ptx_lex_init(&(ptx_parser->scanner));
+ ptx_parser->init_directive_state();
+ ptx_parser->init_instruction_state();
+ FILE *ptx_in;
ptx_in = fopen(ptx_filename, "r");
- ptx_parse();
+ ptx_set_in(ptx_in, ptx_parser->scanner);
+ ptx_parse(ptx_parser->scanner, ptx_parser);
+ ptx_in = ptx_get_in(ptx_parser->scanner);
+ ptx_lex_destroy(ptx_parser->scanner);
fclose(ptx_in);
- return g_global_symbol_table;
+ return ptx_parser->g_global_symbol_table;
}
-static int g_entry_point;
-void start_function( int entry_point )
+void ptx_recognizer::start_function( int entry_point )
{
PTX_PARSE_DPRINTF("start_function");
init_directive_state();
@@ -190,11 +160,7 @@ void start_function( int entry_point )
g_entry_func_param_index=0;
}
-char *g_add_identifier_cached__identifier = NULL;
-int g_add_identifier_cached__array_dim;
-int g_add_identifier_cached__array_ident;
-
-void add_function_name( const char *name )
+void ptx_recognizer::add_function_name( const char *name )
{
PTX_PARSE_DPRINTF("add_function_name %s %s", name, ((g_entry_point==1)?"(entrypoint)":((g_entry_point==2)?"(extern)":"")));
bool prior_decl = g_global_symbol_table->add_function_decl( name, g_entry_point, &g_func_info, &g_current_symbol_table );
@@ -210,21 +176,21 @@ void add_function_name( const char *name )
if( prior_decl ) {
g_func_info->remove_args();
}
- g_global_symbol_table->add_function( g_func_info, g_filename, ptx_lineno );
+ g_global_symbol_table->add_function( g_func_info, gpgpu_ctx->g_filename, ptx_get_lineno(scanner) );
}
//Jin: handle instruction group for cdp
-void start_inst_group() {
+void ptx_recognizer::start_inst_group() {
PTX_PARSE_DPRINTF("start_instruction_group");
g_current_symbol_table = g_current_symbol_table->start_inst_group();
}
-void end_inst_group() {
+void ptx_recognizer::end_inst_group() {
PTX_PARSE_DPRINTF("end_instruction_group");
g_current_symbol_table = g_current_symbol_table->end_inst_group();
}
-void add_directive()
+void ptx_recognizer::add_directive()
{
PTX_PARSE_DPRINTF("add_directive");
init_directive_state();
@@ -232,7 +198,7 @@ void add_directive()
#define mymax(a,b) ((a)>(b)?(a):(b))
-void end_function()
+void ptx_recognizer::end_function()
{
PTX_PARSE_DPRINTF("end_function");
@@ -250,7 +216,7 @@ void end_function()
#define parse_error(msg, ...) parse_error_impl(__FILE__,__LINE__, msg, ##__VA_ARGS__)
#define parse_assert(cond,msg, ...) parse_assert_impl((cond),__FILE__,__LINE__, msg, ##__VA_ARGS__)
-void parse_error_impl( const char *file, unsigned line, const char *msg, ... )
+void ptx_recognizer::parse_error_impl( const char *file, unsigned line, const char *msg, ... )
{
va_list ap;
char buf[1024];
@@ -259,13 +225,13 @@ void parse_error_impl( const char *file, unsigned line, const char *msg, ... )
va_end(ap);
g_error_detected = 1;
- printf("%s:%u: Parse error: %s (%s:%u)\n\n", g_filename, ptx_lineno, buf, file, line);
- ptx_error(NULL);
+ printf("%s:%u: Parse error: %s (%s:%u)\n\n", gpgpu_ctx->g_filename, ptx_get_lineno(scanner), buf, file, line);
+ ptx_error(scanner, NULL);
abort();
exit(1);
}
-void parse_assert_impl( int test_value, const char *file, unsigned line, const char *msg, ... )
+void ptx_recognizer::parse_assert_impl( int test_value, const char *file, unsigned line, const char *msg, ... )
{
va_list ap;
char buf[1024];
@@ -277,19 +243,17 @@ void parse_assert_impl( int test_value, const char *file, unsigned line, const c
parse_error_impl(file,line, msg);
}
-extern char linebuf[4096];
-void set_return()
+void ptx_recognizer::set_return()
{
parse_assert( (g_opcode == CALL_OP || g_opcode == CALLP_OP), "only call can have return value");
g_operands.front().set_return();
g_return_var = g_operands.front();
}
-std::map<std::string,std::map<unsigned,const ptx_instruction*> > g_inst_lookup;
-const ptx_instruction *ptx_instruction_lookup( const char *filename, unsigned linenumber )
+const ptx_instruction *ptx_recognizer::ptx_instruction_lookup( const char *filename, unsigned linenumber )
{
std::map<std::string,std::map<unsigned,const ptx_instruction*> >::iterator f=g_inst_lookup.find(filename);
if( f == g_inst_lookup.end() )
@@ -300,7 +264,7 @@ const ptx_instruction *ptx_instruction_lookup( const char *filename, unsigned li
return l->second;
}
-void add_instruction()
+void ptx_recognizer::add_instruction()
{
PTX_PARSE_DPRINTF("add_instruction: %s", ((g_opcode>0)?g_opcode_string[g_opcode]:"<label>") );
assert( g_shader_core_config != 0 );
@@ -315,16 +279,17 @@ void add_instruction()
g_wmma_options,
g_scalar_type,
g_space_spec,
- g_filename,
- ptx_lineno,
+ gpgpu_ctx->g_filename,
+ ptx_get_lineno(scanner),
linebuf,
- g_shader_core_config );
+ g_shader_core_config,
+ gpgpu_ctx );
g_instructions.push_back(i);
- g_inst_lookup[g_filename][ptx_lineno] = i;
+ g_inst_lookup[gpgpu_ctx->g_filename][ptx_get_lineno(scanner)] = i;
init_instruction_state();
}
-void add_variables()
+void ptx_recognizer::add_variables()
{
PTX_PARSE_DPRINTF("add_variables");
if ( !g_operands.empty() ) {
@@ -334,7 +299,7 @@ void add_variables()
init_directive_state();
}
-void set_variable_type()
+void ptx_recognizer::set_variable_type()
{
PTX_PARSE_DPRINTF("set_variable_type space_spec=%s scalar_type_spec=%s",
g_ptx_token_decode[g_space_spec.get_type()].c_str(),
@@ -348,19 +313,12 @@ void set_variable_type()
g_extern_spec );
}
-bool check_for_duplicates( const char *identifier )
+bool ptx_recognizer::check_for_duplicates( const char *identifier )
{
const symbol *s = g_current_symbol_table->lookup(identifier);
return ( s != NULL );
}
-extern std::set<std::string> g_globals;
-extern std::set<std::string> g_constants;
-
-int g_func_decl = 0;
-int g_ident_add_uid = 0;
-unsigned g_const_alloc = 1;
-
// Returns padding that needs to be inserted ahead of address to make it aligned to min(size, maxalign)
/*
* @param address the address in bytes
@@ -378,7 +336,7 @@ int pad_address (new_addr_type address, unsigned size, unsigned maxalign) {
return alignto ? ((alignto - (address % alignto)) % alignto) : 0;
}
-void add_identifier( const char *identifier, int array_dim, unsigned array_ident )
+void ptx_recognizer::add_identifier( const char *identifier, int array_dim, unsigned array_ident )
{
if(array_ident==ARRAY_IDENTIFIER){
g_size *= array_dim;
@@ -426,7 +384,7 @@ void add_identifier( const char *identifier, int array_dim, unsigned array_ident
default:
break;
}
- g_last_symbol = g_current_symbol_table->add_variable(identifier,type,num_bits/8,g_filename,ptx_lineno);
+ g_last_symbol = g_current_symbol_table->add_variable(identifier,type,num_bits/8,gpgpu_ctx->g_filename,ptx_get_lineno(scanner));
switch ( ti.get_memory_space().get_type() ) {
case reg_space: {
regnum = g_current_symbol_table->next_reg_num();
@@ -489,7 +447,7 @@ void add_identifier( const char *identifier, int array_dim, unsigned array_ident
g_current_symbol_table->alloc_global( num_bits/8 + addr_pad );
}
if( g_current_symbol_table == g_global_symbol_table ) {
- g_constants.insert( identifier );
+ gpgpu_ctx->func_sim->g_constants.insert( identifier );
}
assert( g_current_symbol_table != NULL );
g_sym_name_to_symbol_table[ identifier ] = g_current_symbol_table;
@@ -507,7 +465,7 @@ void add_identifier( const char *identifier, int array_dim, unsigned array_ident
fflush(stdout);
g_last_symbol->set_address( addr+addr_pad );
g_current_symbol_table->alloc_global( num_bits/8 + addr_pad );
- g_globals.insert( identifier );
+ gpgpu_ctx->func_sim->g_globals.insert( identifier );
assert( g_current_symbol_table != NULL );
g_sym_name_to_symbol_table[ identifier ] = g_current_symbol_table;
break;
@@ -569,7 +527,7 @@ void add_identifier( const char *identifier, int array_dim, unsigned array_ident
}
}
-void add_constptr(const char* identifier1, const char* identifier2, int offset)
+void ptx_recognizer::add_constptr(const char* identifier1, const char* identifier2, int offset)
{
symbol *s1 = g_current_symbol_table->lookup(identifier1);
const symbol *s2 = g_current_symbol_table->lookup(identifier2);
@@ -584,7 +542,7 @@ void add_constptr(const char* identifier1, const char* identifier2, int offset)
s1->set_address( addr + offset );
}
-void add_function_arg()
+void ptx_recognizer::add_function_arg()
{
assert(g_size>0);
if( g_func_info ) {
@@ -597,20 +555,20 @@ void add_function_arg()
}
-void add_extern_spec()
+void ptx_recognizer::add_extern_spec()
{
PTX_PARSE_DPRINTF("add_extern_spec");
g_extern_spec = 1;
}
-void add_alignment_spec( int spec )
+void ptx_recognizer::add_alignment_spec( int spec )
{
PTX_PARSE_DPRINTF("add_alignment_spec");
parse_assert( g_alignment_spec == -1, "multiple .align specifiers per variable declaration not allowed." );
g_alignment_spec = spec;
}
-void add_ptr_spec( enum _memory_space_t spec )
+void ptx_recognizer::add_ptr_spec( enum _memory_space_t spec )
{
PTX_PARSE_DPRINTF("add_ptr_spec \"%s\"", g_ptx_token_decode[spec].c_str() );
parse_assert( g_ptr_spec == undefined_space, "multiple ptr space specifiers not allowed." );
@@ -618,7 +576,7 @@ void add_ptr_spec( enum _memory_space_t spec )
g_ptr_spec = spec;
}
-void add_space_spec( enum _memory_space_t spec, int value )
+void ptx_recognizer::add_space_spec( enum _memory_space_t spec, int value )
{
PTX_PARSE_DPRINTF("add_space_spec \"%s\"", g_ptx_token_decode[spec].c_str() );
parse_assert( g_space_spec == undefined_space, "multiple space specifiers not allowed." );
@@ -637,14 +595,14 @@ void add_space_spec( enum _memory_space_t spec, int value )
}
}
-void add_vector_spec(int spec )
+void ptx_recognizer::add_vector_spec(int spec )
{
PTX_PARSE_DPRINTF("add_vector_spec");
parse_assert( g_vector_spec == -1, "multiple vector specifiers not allowed." );
g_vector_spec = spec;
}
-void add_scalar_type_spec( int type_spec )
+void ptx_recognizer::add_scalar_type_spec( int type_spec )
{
//save size of parameter
switch ( type_spec ) {
@@ -682,23 +640,23 @@ void add_scalar_type_spec( int type_spec )
g_scalar_type_spec = type_spec;
}
-void add_label( const char *identifier )
+void ptx_recognizer::add_label( const char *identifier )
{
PTX_PARSE_DPRINTF("add_label");
symbol *s = g_current_symbol_table->lookup(identifier);
if ( s != NULL ) {
g_label = s;
} else {
- g_label = g_current_symbol_table->add_variable(identifier,NULL,0,g_filename,ptx_lineno);
+ g_label = g_current_symbol_table->add_variable(identifier,NULL,0,gpgpu_ctx->g_filename,ptx_get_lineno(scanner));
}
}
-void add_opcode( int opcode )
+void ptx_recognizer::add_opcode( int opcode )
{
g_opcode = opcode;
}
-void add_pred( const char *identifier, int neg, int predModifier )
+void ptx_recognizer::add_pred( const char *identifier, int neg, int predModifier )
{
PTX_PARSE_DPRINTF("add_pred");
const symbol *s = g_current_symbol_table->lookup(identifier);
@@ -711,17 +669,17 @@ void add_pred( const char *identifier, int neg, int predModifier )
g_pred_mod = predModifier;
}
-void add_option( int option )
+void ptx_recognizer::add_option( int option )
{
PTX_PARSE_DPRINTF("add_option");
g_options.push_back( option );
}
-void add_wmma_option( int option )
+void ptx_recognizer::add_wmma_option( int option )
{
PTX_PARSE_DPRINTF("add_option");
g_wmma_options.push_back( option );
}
-void add_double_operand( const char *d1, const char *d2 )
+void ptx_recognizer::add_double_operand( const char *d1, const char *d2 )
{
//operands that access two variables.
//eg. s[$ofs1+$r0], g[$ofs1+=$r0]
@@ -731,38 +689,38 @@ void add_double_operand( const char *d1, const char *d2 )
const symbol *s1 = g_current_symbol_table->lookup(d1);
const symbol *s2 = g_current_symbol_table->lookup(d2);
parse_assert( s1 != NULL && s2 != NULL, "component(s) missing declarations.");
- g_operands.push_back( operand_info(s1,s2) );
+ g_operands.push_back( operand_info(s1,s2,gpgpu_ctx) );
}
-void add_1vector_operand( const char *d1 )
+void ptx_recognizer::add_1vector_operand( const char *d1 )
{
// handles the single element vector operand ({%v1}) found in tex.1d instructions
PTX_PARSE_DPRINTF("add_1vector_operand");
const symbol *s1 = g_current_symbol_table->lookup(d1);
parse_assert( s1 != NULL, "component(s) missing declarations.");
- g_operands.push_back( operand_info(s1,NULL,NULL,NULL) );
+ g_operands.push_back( operand_info(s1,NULL,NULL,NULL,gpgpu_ctx) );
}
-void add_2vector_operand( const char *d1, const char *d2 )
+void ptx_recognizer::add_2vector_operand( const char *d1, const char *d2 )
{
PTX_PARSE_DPRINTF("add_2vector_operand");
const symbol *s1 = g_current_symbol_table->lookup(d1);
const symbol *s2 = g_current_symbol_table->lookup(d2);
parse_assert( s1 != NULL && s2 != NULL, "v2 component(s) missing declarations.");
- g_operands.push_back( operand_info(s1,s2,NULL,NULL) );
+ g_operands.push_back( operand_info(s1,s2,NULL,NULL,gpgpu_ctx) );
}
-void add_3vector_operand( const char *d1, const char *d2, const char *d3 )
+void ptx_recognizer::add_3vector_operand( const char *d1, const char *d2, const char *d3 )
{
PTX_PARSE_DPRINTF("add_3vector_operand");
const symbol *s1 = g_current_symbol_table->lookup(d1);
const symbol *s2 = g_current_symbol_table->lookup(d2);
const symbol *s3 = g_current_symbol_table->lookup(d3);
parse_assert( s1 != NULL && s2 != NULL && s3 != NULL, "v3 component(s) missing declarations.");
- g_operands.push_back( operand_info(s1,s2,s3,NULL) );
+ g_operands.push_back( operand_info(s1,s2,s3,NULL,gpgpu_ctx) );
}
-void add_4vector_operand( const char *d1, const char *d2, const char *d3, const char *d4 )
+void ptx_recognizer::add_4vector_operand( const char *d1, const char *d2, const char *d3, const char *d4 )
{
PTX_PARSE_DPRINTF("add_4vector_operand");
const symbol *s1 = g_current_symbol_table->lookup(d1);
@@ -774,9 +732,9 @@ void add_4vector_operand( const char *d1, const char *d2, const char *d3, const
if ( s2 == null_op ) s2 = NULL;
if ( s3 == null_op ) s3 = NULL;
if ( s4 == null_op ) s4 = NULL;
- g_operands.push_back( operand_info(s1,s2,s3,s4) );
+ g_operands.push_back( operand_info(s1,s2,s3,s4,gpgpu_ctx) );
}
-void add_8vector_operand( const char *d1, const char *d2, const char *d3, const char *d4,const char *d5,const char *d6,const char *d7,const char *d8 )
+void ptx_recognizer::add_8vector_operand( const char *d1, const char *d2, const char *d3, const char *d4,const char *d5,const char *d6,const char *d7,const char *d8 )
{
PTX_PARSE_DPRINTF("add_8vector_operand");
const symbol *s1 = g_current_symbol_table->lookup(d1);
@@ -796,16 +754,16 @@ void add_8vector_operand( const char *d1, const char *d2, const char *d3, const
if ( s6 == null_op ) s6 = NULL;
if ( s7 == null_op ) s7 = NULL;
if ( s8 == null_op ) s8 = NULL;
- g_operands.push_back( operand_info(s1,s2,s3,s4,s5,s6,s7,s8) );
+ g_operands.push_back( operand_info(s1,s2,s3,s4,s5,s6,s7,s8,gpgpu_ctx) );
}
-void add_builtin_operand( int builtin, int dim_modifier )
+void ptx_recognizer::add_builtin_operand( int builtin, int dim_modifier )
{
PTX_PARSE_DPRINTF("add_builtin_operand");
- g_operands.push_back( operand_info(builtin,dim_modifier) );
+ g_operands.push_back( operand_info(builtin,dim_modifier,gpgpu_ctx) );
}
-void add_memory_operand()
+void ptx_recognizer::add_memory_operand()
{
PTX_PARSE_DPRINTF("add_memory_operand");
assert( !g_operands.empty() );
@@ -813,7 +771,7 @@ void add_memory_operand()
}
/*TODO: add other memory locations*/
-void change_memory_addr_space(const char *identifier)
+void ptx_recognizer::change_memory_addr_space(const char *identifier)
{
/*0 = N/A, not reading from memory
*1 = global memory
@@ -860,7 +818,7 @@ void change_memory_addr_space(const char *identifier)
parse_assert(recognizedType, "Error: unrecognized memory type.");
}
-void change_operand_lohi( int lohi )
+void ptx_recognizer::change_operand_lohi( int lohi )
{
/*0 = N/A, read entire operand
*1 = lo, reading from lowest bits
@@ -874,14 +832,14 @@ void change_operand_lohi( int lohi )
}
-void set_immediate_operand_type ()
+void ptx_recognizer::set_immediate_operand_type ()
{
PTX_PARSE_DPRINTF("set_immediate_operand_type");
assert( !g_operands.empty() );
g_operands.back().set_immediate_addr();
}
-void change_double_operand_type( int operand_type )
+void ptx_recognizer::change_double_operand_type( int operand_type )
{
/*
*-3 = reg / reg (set instruction, but both get same value)
@@ -913,7 +871,7 @@ void change_double_operand_type( int operand_type )
}
-void change_operand_neg( )
+void ptx_recognizer::change_operand_neg( )
{
PTX_PARSE_DPRINTF("change_operand_neg");
assert( !g_operands.empty() );
@@ -922,53 +880,53 @@ void change_operand_neg( )
}
-void add_literal_int( int value )
+void ptx_recognizer::add_literal_int( int value )
{
PTX_PARSE_DPRINTF("add_literal_int");
- g_operands.push_back( operand_info(value) );
+ g_operands.push_back( operand_info(value,gpgpu_ctx) );
}
-void add_literal_float( float value )
+void ptx_recognizer::add_literal_float( float value )
{
PTX_PARSE_DPRINTF("add_literal_float");
- g_operands.push_back( operand_info(value) );
+ g_operands.push_back( operand_info(value,gpgpu_ctx) );
}
-void add_literal_double( double value )
+void ptx_recognizer::add_literal_double( double value )
{
PTX_PARSE_DPRINTF("add_literal_double");
- g_operands.push_back( operand_info(value) );
+ g_operands.push_back( operand_info(value,gpgpu_ctx) );
}
-void add_scalar_operand( const char *identifier )
+void ptx_recognizer::add_scalar_operand( const char *identifier )
{
PTX_PARSE_DPRINTF("add_scalar_operand");
const symbol *s = g_current_symbol_table->lookup(identifier);
if ( s == NULL ) {
if ( g_opcode == BRA_OP || g_opcode == CALLP_OP) {
// forward branch target...
- s = g_current_symbol_table->add_variable(identifier,NULL,0,g_filename,ptx_lineno);
+ s = g_current_symbol_table->add_variable(identifier,NULL,0,gpgpu_ctx->g_filename,ptx_get_lineno(scanner));
} else {
std::string msg = std::string("operand \"") + identifier + "\" has no declaration.";
parse_error( msg.c_str() );
}
}
- g_operands.push_back( operand_info(s) );
+ g_operands.push_back( operand_info(s,gpgpu_ctx) );
}
-void add_neg_pred_operand( const char *identifier )
+void ptx_recognizer::add_neg_pred_operand( const char *identifier )
{
PTX_PARSE_DPRINTF("add_neg_pred_operand");
const symbol *s = g_current_symbol_table->lookup(identifier);
if ( s == NULL ) {
- s = g_current_symbol_table->add_variable(identifier,NULL,1,g_filename,ptx_lineno);
+ s = g_current_symbol_table->add_variable(identifier,NULL,1,gpgpu_ctx->g_filename,ptx_get_lineno(scanner));
}
- operand_info op(s);
+ operand_info op(s, gpgpu_ctx);
op.set_neg_pred();
g_operands.push_back( op );
}
-void add_address_operand( const char *identifier, int offset )
+void ptx_recognizer::add_address_operand( const char *identifier, int offset )
{
PTX_PARSE_DPRINTF("add_address_operand");
const symbol *s = g_current_symbol_table->lookup(identifier);
@@ -976,28 +934,28 @@ void add_address_operand( const char *identifier, int offset )
std::string msg = std::string("operand \"") + identifier + "\" has no declaration.";
parse_error( msg.c_str() );
}
- g_operands.push_back( operand_info(s,offset) );
+ g_operands.push_back( operand_info(s,offset,gpgpu_ctx) );
}
-void add_address_operand2( int offset )
+void ptx_recognizer::add_address_operand2( int offset )
{
PTX_PARSE_DPRINTF("add_address_operand");
- g_operands.push_back( operand_info((unsigned)offset) );
+ g_operands.push_back( operand_info((unsigned)offset,gpgpu_ctx) );
}
-void add_array_initializer()
+void ptx_recognizer::add_array_initializer()
{
g_last_symbol->add_initializer(g_operands);
}
-void add_version_info( float ver, unsigned ext )
+void ptx_recognizer::add_version_info( float ver, unsigned ext )
{
g_global_symbol_table->set_ptx_version(ver,ext);
}
-void add_file( unsigned num, const char *filename )
+void ptx_recognizer::add_file( unsigned num, const char *filename )
{
- if( g_filename == NULL ) {
+ if( gpgpu_ctx->g_filename == NULL ) {
char *b = strdup(filename);
char *l=b;
char *n=b;
@@ -1013,7 +971,7 @@ void add_file( unsigned num, const char *filename )
char *q = strtok(NULL,".");
if( q && !strcmp(q,"cu") ) {
- g_filename = strdup(buf);
+ gpgpu_ctx->g_filename = strdup(buf);
}
free( b );
@@ -1022,44 +980,44 @@ void add_file( unsigned num, const char *filename )
g_current_symbol_table = g_global_symbol_table;
}
-void *reset_symtab()
+void * ptx_recognizer::reset_symtab()
{
void *result = g_current_symbol_table;
g_current_symbol_table = g_global_symbol_table;
return result;
}
-void set_symtab(void*symtab)
+void ptx_recognizer::set_symtab(void*symtab)
{
g_current_symbol_table = (symbol_table*)symtab;
}
-void add_pragma( const char *str )
+void ptx_recognizer::add_pragma( const char *str )
{
printf("GPGPU-Sim PTX: Warning -- ignoring pragma '%s'\n", str );
}
-void version_header(double a) {} //intentional dummy function
+void ptx_recognizer::version_header(double a) {} //intentional dummy function
-void target_header(char* a)
+void ptx_recognizer::target_header(char* a)
{
g_global_symbol_table->set_sm_target(a,NULL,NULL);
}
-void target_header2(char* a, char* b)
+void ptx_recognizer::target_header2(char* a, char* b)
{
g_global_symbol_table->set_sm_target(a,b,NULL);
}
-void target_header3(char* a, char* b, char* c)
+void ptx_recognizer::target_header3(char* a, char* b, char* c)
{
g_global_symbol_table->set_sm_target(a,b,c);
}
-void maxnt_id(int x, int y, int z) {
+void ptx_recognizer::maxnt_id(int x, int y, int z) {
g_func_info->set_maxnt_id(x * y * z);
}
-void func_header(const char* a) {} //intentional dummy function
-void func_header_info(const char* a) {} //intentional dummy function
-void func_header_info_int(const char* a, int b) {} //intentional dummy function
+void ptx_recognizer::func_header(const char* a) {} //intentional dummy function
+void ptx_recognizer::func_header_info(const char* a) {} //intentional dummy function
+void ptx_recognizer::func_header_info_int(const char* a, int b) {} //intentional dummy function
diff --git a/src/cuda-sim/ptx_parser.h b/src/cuda-sim/ptx_parser.h
index 7b6e3a2..11a3d20 100644
--- a/src/cuda-sim/ptx_parser.h
+++ b/src/cuda-sim/ptx_parser.h
@@ -29,77 +29,159 @@
#define ptx_parser_INCLUDED
#include "../abstract_hardware_model.h"
-extern const char *g_filename;
-extern int g_error_detected;
+#include "ptx_ir.h"
-#ifdef __cplusplus
-class symbol_table* init_parser(const char*);
-const class ptx_instruction *ptx_instruction_lookup( const char *filename, unsigned linenumber );
-#endif
+class gpgpu_context;
+typedef void * yyscan_t;
+class ptx_recognizer {
+ public:
+ ptx_recognizer( gpgpu_context* ctx ) : g_return_var(ctx) {
+ scanner = NULL;
+ g_size = -1;
+ g_add_identifier_cached__identifier = NULL;
+ g_alignment_spec = -1;
+ g_var_type = NULL;
+ g_opcode = -1;
+ g_space_spec = undefined_space;
+ g_ptr_spec = undefined_space;
+ g_scalar_type_spec = -1;
+ g_vector_spec = -1;
+ g_extern_spec = 0;
+ g_func_decl = 0;
+ g_ident_add_uid = 0;
+ g_const_alloc = 1;
+ g_max_regs_per_thread = 0;
+ g_global_symbol_table = NULL;
+ g_current_symbol_table = NULL;
+ g_last_symbol = NULL;
+ g_error_detected = 0;
+ g_entry_func_param_index=0;
+ g_func_info = NULL;
+ g_debug_ir_generation=false;
+ gpgpu_ctx = ctx;
+ }
+ // global list
+ yyscan_t scanner;
+#define PTX_LINEBUF_SIZE (4*1024)
+ char linebuf[PTX_LINEBUF_SIZE];
+ unsigned col;
+ int g_size;
+ char *g_add_identifier_cached__identifier;
+ int g_add_identifier_cached__array_dim;
+ int g_add_identifier_cached__array_ident;
+ int g_alignment_spec;
+ // variable declaration stuff:
+ type_info *g_var_type;
+ // instruction definition stuff:
+ const symbol *g_pred;
+ int g_neg_pred;
+ int g_pred_mod;
+ symbol *g_label;
+ int g_opcode;
+ std::list<operand_info> g_operands;
+ std::list<int> g_options;
+ std::list<int> g_wmma_options;
+ std::list<int> g_scalar_type;
+ // type specifier stuff:
+ memory_space_t g_space_spec;
+ memory_space_t g_ptr_spec;
+ int g_scalar_type_spec;
+ int g_vector_spec;
+ int g_extern_spec;
+ int g_func_decl;
+ int g_ident_add_uid;
+ unsigned g_const_alloc;
+ unsigned g_max_regs_per_thread;
+ symbol_table *g_global_symbol_table;
+ symbol_table *g_current_symbol_table;
+ symbol *g_last_symbol;
+ std::list<ptx_instruction*> g_instructions;
+ int g_error_detected;
+ unsigned g_entry_func_param_index;
+ function_info *g_func_info;
+ operand_info g_return_var;
+ bool g_debug_ir_generation;
+ int g_entry_point;
+ const struct core_config *g_shader_core_config;
+ std::map<std::string,std::map<unsigned,const ptx_instruction*> > g_inst_lookup;
+ // the program intermediate representation...
+ std::map<std::string,symbol_table*> g_sym_name_to_symbol_table;
+ // backward pointer
+ class gpgpu_context* gpgpu_ctx;
+
+ // member function list
+ void init_directive_state();
+ void init_instruction_state();
+ void start_function( int entry_point );
+ void add_function_name( const char *fname );
+ void add_directive();
+ void end_function();
+ void add_identifier( const char *s, int array_dim, unsigned array_ident );
+ void add_function_arg();
+ void add_scalar_type_spec( int type_spec );
+ void add_scalar_operand( const char *identifier );
+ void add_neg_pred_operand( const char *identifier );
+ void add_variables();
+ void set_variable_type();
+ void add_opcode( int opcode );
+ void add_pred( const char *identifier, int negate, int predModifier );
+ void add_1vector_operand( const char *d1 );
+ void add_2vector_operand( const char *d1, const char *d2 );
+ void add_3vector_operand( const char *d1, const char *d2, const char *d3 );
+ void add_4vector_operand( const char *d1, const char *d2, const char *d3, const char *d4 );
+ void add_8vector_operand( const char *d1, const char *d2, const char *d3, const char *d4 ,const char *d5,const char *d6,const char *d7,const char *d8);
+ void add_option(int option );
+ void add_wmma_option(int option );
+ void add_builtin_operand( int builtin, int dim_modifier );
+ void add_memory_operand( );
+ void add_literal_int( int value );
+ void add_literal_float( float value );
+ void add_literal_double( double value );
+ void add_address_operand( const char *identifier, int offset );
+ void add_address_operand2( int offset );
+ void add_label( const char *idenfiier );
+ void add_vector_spec(int spec );
+ void add_space_spec( enum _memory_space_t spec, int value );
+ void add_ptr_spec( enum _memory_space_t spec );
+ void add_extern_spec();
+ void add_instruction();
+ void set_return();
+ void add_alignment_spec( int spec );
+ void add_array_initializer();
+ void add_file( unsigned num, const char *filename );
+ void add_version_info( float ver, unsigned ext);
+ void *reset_symtab();
+ void set_symtab(void*);
+ void add_pragma( const char *str );
+ void func_header(const char* a);
+ void func_header_info(const char* a);
+ void func_header_info_int(const char* a, int b);
+ void add_constptr(const char* identifier1, const char* identifier2, int offset);
+ void target_header(char* a);
+ void target_header2(char* a, char* b);
+ void target_header3(char* a, char* b, char* c);
+ void add_double_operand( const char *d1, const char *d2 );
+ void change_memory_addr_space( const char *identifier );
+ void change_operand_lohi( int lohi );
+ void change_double_operand_type( int addr_type );
+ void change_operand_neg( );
+ void set_immediate_operand_type( );
+ void version_header(double a);
+ void maxnt_id(int x, int y, int z);
+ void parse_error_impl( const char *file, unsigned line, const char *msg, ... );
+ void parse_assert_impl( int test_value, const char *file, unsigned line, const char *msg, ... );
+ //Jin: handle instructino group for cdp
+ void start_inst_group();
+ void end_inst_group();
+ bool check_for_duplicates( const char *identifier );
+ void read_parser_environment_variables();
+ void set_ptx_warp_size(const struct core_config * warp_size);
+ const class ptx_instruction *ptx_instruction_lookup( const char *filename, unsigned linenumber );
+
+};
const char *decode_token( int type );
void read_parser_environment_variables();
-void start_function( int entry_point );
-void add_function_name( const char *fname );
-void init_directive_state();
-void add_directive();
-void end_function();
-void add_identifier( const char *s, int array_dim, unsigned array_ident );
-void add_function_arg();
-void add_scalar_type_spec( int type_spec );
-void add_scalar_operand( const char *identifier );
-void add_neg_pred_operand( const char *identifier );
-void add_variables();
-void set_variable_type();
-void add_opcode( int opcode );
-void add_pred( const char *identifier, int negate, int predModifier );
-void add_1vector_operand( const char *d1 );
-void add_2vector_operand( const char *d1, const char *d2 );
-void add_3vector_operand( const char *d1, const char *d2, const char *d3 );
-void add_4vector_operand( const char *d1, const char *d2, const char *d3, const char *d4 );
-void add_8vector_operand( const char *d1, const char *d2, const char *d3, const char *d4 ,const char *d5,const char *d6,const char *d7,const char *d8);
-void add_option(int option );
-void add_wmma_option(int option );
-void add_builtin_operand( int builtin, int dim_modifier );
-void add_memory_operand( );
-void add_literal_int( int value );
-void add_literal_float( float value );
-void add_literal_double( double value );
-void add_address_operand( const char *identifier, int offset );
-void add_address_operand2( int offset );
-void add_label( const char *idenfiier );
-void add_vector_spec(int spec );
-void add_space_spec( enum _memory_space_t spec, int value );
-void add_ptr_spec( enum _memory_space_t spec );
-void add_extern_spec();
-void add_instruction();
-void set_return();
-void add_alignment_spec( int spec );
-void add_array_initializer();
-void add_file( unsigned num, const char *filename );
-void add_version_info( float ver, unsigned ext);
-void *reset_symtab();
-void set_symtab(void*);
-void add_pragma( const char *str );
-void func_header(const char* a);
-void func_header_info(const char* a);
-void func_header_info_int(const char* a, int b);
-void add_constptr(const char* identifier1, const char* identifier2, int offset);
-void target_header(char* a);
-void target_header2(char* a, char* b);
-void target_header3(char* a, char* b, char* c);
-void add_double_operand( const char *d1, const char *d2 );
-void change_memory_addr_space( const char *identifier );
-void change_operand_lohi( int lohi );
-void change_double_operand_type( int addr_type );
-void change_operand_neg( );
-void set_immediate_operand_type( );
-void version_header(double a);
-void maxnt_id(int x, int y, int z);
-
-//Jin: handle instructino group for cdp
-void start_inst_group();
-void end_inst_group();
#define NON_ARRAY_IDENTIFIER 1
#define ARRAY_IDENTIFIER_NO_DIM 2
diff --git a/src/cuda-sim/ptx_sim.cc b/src/cuda-sim/ptx_sim.cc
index 820287d..949ee66 100644
--- a/src/cuda-sim/ptx_sim.cc
+++ b/src/cuda-sim/ptx_sim.cc
@@ -28,23 +28,25 @@
#include "ptx_sim.h"
#include <string>
#include "ptx_ir.h"
+class ptx_recognizer;
+typedef void * yyscan_t;
#include "ptx.tab.h"
#include "../gpgpu-sim/gpu-sim.h"
#include "../gpgpu-sim/shader.h"
+#include "../../libcuda/gpgpu_context.h"
void feature_not_implemented( const char *f );
-std::set<unsigned long long> g_ptx_cta_info_sm_idx_used;
-unsigned long long g_ptx_cta_info_uid = 1;
-ptx_cta_info::ptx_cta_info( unsigned sm_idx )
+ptx_cta_info::ptx_cta_info( unsigned sm_idx, gpgpu_context* ctx )
{
- assert( g_ptx_cta_info_sm_idx_used.find(sm_idx) == g_ptx_cta_info_sm_idx_used.end() );
- g_ptx_cta_info_sm_idx_used.insert(sm_idx);
+ assert( ctx->func_sim->g_ptx_cta_info_sm_idx_used.find(sm_idx) == ctx->func_sim->g_ptx_cta_info_sm_idx_used.end() );
+ ctx->func_sim->g_ptx_cta_info_sm_idx_used.insert(sm_idx);
m_sm_idx = sm_idx;
- m_uid = g_ptx_cta_info_uid++;
+ m_uid = (ctx->g_ptx_cta_info_uid)++;
m_bar_threads = 0;
+ gpgpu_ctx = ctx;
}
void ptx_cta_info::add_thread( ptx_thread_info *thd )
@@ -164,18 +166,16 @@ void ptx_warp_info::reset_done_threads()
m_done_threads = 0;
}
-unsigned g_ptx_thread_info_uid_next=1;
-unsigned g_ptx_thread_info_delete_count=0;
ptx_thread_info::~ptx_thread_info()
{
- g_ptx_thread_info_delete_count++;
+ m_gpu->gpgpu_ctx->func_sim->g_ptx_thread_info_delete_count++;
}
ptx_thread_info::ptx_thread_info( kernel_info_t &kernel )
: m_kernel(kernel)
{
- m_uid = g_ptx_thread_info_uid_next++;
+ m_uid = kernel.entry()->gpgpu_ctx->func_sim->g_ptx_thread_info_uid_next++;
m_core = NULL;
m_barrier_num = -1;
m_at_barrier = false;
@@ -222,7 +222,7 @@ void ptx_thread_info::set_done()
{
assert( !m_at_barrier );
m_thread_done = true;
- m_cycle_done = gpu_sim_cycle;
+ m_cycle_done = m_gpu->gpu_sim_cycle;
}
unsigned ptx_thread_info::get_builtin( int builtin_id, unsigned dim_mod )
@@ -230,15 +230,15 @@ unsigned ptx_thread_info::get_builtin( int builtin_id, unsigned dim_mod )
assert( m_valid );
switch ((builtin_id&0xFFFF)) {
case CLOCK_REG:
- return (unsigned)(gpu_sim_cycle + gpu_tot_sim_cycle);
+ return (unsigned)(m_gpu->gpu_sim_cycle + m_gpu->gpu_tot_sim_cycle);
case CLOCK64_REG:
abort(); // change return value to unsigned long long?
// GPGPUSim clock is 4 times slower - multiply by 4
- return (gpu_sim_cycle + gpu_tot_sim_cycle)*4;
+ return (m_gpu->gpu_sim_cycle + m_gpu->gpu_tot_sim_cycle)*4;
case HALFCLOCK_ID:
// GPGPUSim clock is 4 times slower - multiply by 4
// Hardware clock counter is incremented at half the shader clock frequency - divide by 2 (Henry '10)
- return (gpu_sim_cycle + gpu_tot_sim_cycle)*2;
+ return (m_gpu->gpu_sim_cycle + m_gpu->gpu_tot_sim_cycle)*2;
case CTAID_REG:
assert( dim_mod < 3 );
if( dim_mod == 0 ) return m_ctaid.x;
@@ -421,9 +421,9 @@ bool ptx_thread_info::callstack_pop()
assert( !((rv_src != NULL) ^ (rv_dst != NULL)) ); // ensure caller and callee agree on whether there is a return value
// read return value from callee frame
- arg_buffer_t buffer;
+ arg_buffer_t buffer(m_gpu->gpgpu_ctx);
if( rv_src != NULL )
- buffer = copy_arg_to_buffer(this, operand_info(rv_src), rv_dst );
+ buffer = copy_arg_to_buffer(this, operand_info(rv_src, m_gpu->gpgpu_ctx), rv_dst );
m_symbol_table = m_callstack.back().m_symbol_table;
m_NPC = m_callstack.back().m_PC;
@@ -455,9 +455,9 @@ bool ptx_thread_info::callstack_pop_plus()
assert( !((rv_src != NULL) ^ (rv_dst != NULL)) ); // ensure caller and callee agree on whether there is a return value
// read return value from callee frame
- arg_buffer_t buffer;
+ arg_buffer_t buffer(m_gpu->gpgpu_ctx);
if( rv_src != NULL )
- buffer = copy_arg_to_buffer(this, operand_info(rv_src), rv_dst );
+ buffer = copy_arg_to_buffer(this, operand_info(rv_src, m_gpu->gpgpu_ctx), rv_dst );
m_symbol_table = m_callstack.back().m_symbol_table;
m_NPC = m_callstack.back().m_PC;
diff --git a/src/cuda-sim/ptx_sim.h b/src/cuda-sim/ptx_sim.h
index d226fbe..c2b3cc8 100644
--- a/src/cuda-sim/ptx_sim.h
+++ b/src/cuda-sim/ptx_sim.h
@@ -164,7 +164,7 @@ class ptx_thread_info;
class ptx_cta_info {
public:
- ptx_cta_info( unsigned sm_idx );
+ ptx_cta_info( unsigned sm_idx, gpgpu_context* ctx );
void add_thread( ptx_thread_info *thd );
unsigned num_threads() const;
void check_cta_thread_status_and_reset();
@@ -176,6 +176,8 @@ public:
void reset_bar_threads();
private:
+ // backward pointer
+ class gpgpu_context* gpgpu_ctx;
unsigned m_bar_threads;
unsigned long long m_uid;
unsigned m_sm_idx;
@@ -341,6 +343,7 @@ public:
dim3 get_ctaid() const { return m_ctaid; }
dim3 get_tid() const { return m_tid; }
+ dim3 get_ntid() const { return m_ntid; }
class gpgpu_sim *get_gpu() { return (gpgpu_sim*)m_gpu;}
unsigned get_hw_tid() const { return m_hw_tid;}
unsigned get_hw_ctaid() const { return m_hw_ctaid;}
diff --git a/src/cuda-sim/ptxinfo.l b/src/cuda-sim/ptxinfo.l
index 33c2748..51371e3 100644
--- a/src/cuda-sim/ptxinfo.l
+++ b/src/cuda-sim/ptxinfo.l
@@ -31,17 +31,23 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
%option noyywrap
%option yylineno
%option prefix="ptxinfo_"
+
+%option bison-bridge
+%option reentrant
+
%{
+#include "ptx_loader.h"
#include "ptxinfo.tab.h"
#include <string.h>
+#include "../../libcuda/gpgpu_context.h"
#define LINEBUF_SIZE 1024
-char ptxinfo_linebuf[LINEBUF_SIZE];
-unsigned ptxinfo_col = 0;
-#define TC if( (ptxinfo_lineno == 1) && ((ptxinfo_col + strlen(ptxinfo_text)) < LINEBUF_SIZE) ) { \
- strncpy(ptxinfo_linebuf+ptxinfo_col,ptxinfo_text,strlen(ptxinfo_text)); \
+#define TC if( (yylineno == 1) && (ptxinfo->col + strlen(yytext) < LINEBUF_SIZE) ) { \
+ strncpy(ptxinfo->linebuf+ptxinfo->col,yytext,strlen(yytext)); \
} \
- ptxinfo_col+=strlen(ptxinfo_text);
+ ptxinfo->col+=strlen(yytext);
+#define YY_DECL int ptxinfo_lex \
+ (YYSTYPE * yylval_param , yyscan_t yyscanner, ptxinfo_data* ptxinfo)
%}
%%
@@ -61,12 +67,12 @@ unsigned ptxinfo_col = 0;
"for" TC; return FOR;
"textures" TC; return TEXTURES;
"error : Duplicate definition of" TC; return DUPLICATE;
-"function" TC; ptxinfo_lval.string_value = strdup(yytext); return FUNCTION;
-"variable" TC; ptxinfo_lval.string_value = strdup(yytext); return VARIABLE;
+"function" TC; yylval->string_value = strdup(yytext); return FUNCTION;
+"variable" TC; yylval->string_value = strdup(yytext); return VARIABLE;
"fatal : Ptx assembly aborted due to errors" TC; return FATAL;
-[_A-Za-z$%][_0-9A-Za-z$]* TC; ptxinfo_lval.string_value = strdup(yytext); return IDENTIFIER;
-[-]{0,1}[0-9]+ TC; ptxinfo_lval.int_value = atoi(yytext); return INT_OPERAND;
+[_A-Za-z$%][_0-9A-Za-z$]* TC; yylval->string_value = strdup(yytext); return IDENTIFIER;
+[-]{0,1}[0-9]+ TC; yylval->int_value = atoi(yytext); return INT_OPERAND;
"+" TC; return PLUS;
"," TC; return COMMA;
@@ -78,26 +84,23 @@ unsigned ptxinfo_col = 0;
" " TC;
"\t" TC;
-\n.* ptxinfo_col=0; strncpy(ptxinfo_linebuf, yytext + 1, 1024); yyless( 1 );
+\n.* ptxinfo->col=0; strncpy(ptxinfo->linebuf, yytext + 1, 1024); yyless( 1 );
%%
-extern int g_ptxinfo_error_detected;
-extern const char *g_filename;
-extern const char *g_ptxinfo_filename;
-
-int ptxinfo_error( const char *s )
+int ptxinfo_error(yyscan_t yyscanner, ptxinfo_data* ptxinfo, const char* msg)
{
+ struct yyguts_t * yyg = (struct yyguts_t*)yyscanner;
int i;
- g_ptxinfo_error_detected = 1;
+ ptxinfo->gpgpu_ctx->func_sim->g_ptxinfo_error_detected = 1;
fflush(stdout);
printf("GPGPU-Sim: ERROR while parsing output of ptxas (used to capture resource usage information)\n");
- if( s != NULL )
- printf("GPGPU-Sim: %s (%s:%u) Syntax error:\n\n", g_filename, g_ptxinfo_filename, ptxinfo_lineno );
- printf(" %s\n", ptxinfo_linebuf );
+ if( msg != NULL )
+ printf("GPGPU-Sim: %s (%s:%u) Syntax error:\n\n", ptxinfo->gpgpu_ctx->g_filename, ptxinfo->g_ptxinfo_filename, yylineno );
+ printf(" %s\n", ptxinfo->linebuf );
printf(" ");
- for( i=0; i < ptxinfo_col-1; i++ ) {
- if( ptxinfo_linebuf[i] == '\t' ) printf("\t");
+ for( i=0; i < ptxinfo->col-1; i++ ) {
+ if( ptxinfo->linebuf[i] == '\t' ) printf("\t");
else printf(" ");
}
diff --git a/src/cuda-sim/ptxinfo.y b/src/cuda-sim/ptxinfo.y
index d241d8c..b303958 100644
--- a/src/cuda-sim/ptxinfo.y
+++ b/src/cuda-sim/ptxinfo.y
@@ -27,6 +27,17 @@ OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
+%{
+typedef void * yyscan_t;
+#include "ptx_loader.h"
+%}
+
+%define api.pure full
+%parse-param {yyscan_t scanner}
+%parse-param {ptxinfo_data* ptxinfo}
+%lex-param {yyscan_t scanner}
+%lex-param {ptxinfo_data* ptxinfo}
+
%union {
int int_value;
char * string_value;
@@ -66,15 +77,14 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
static unsigned g_declared;
static unsigned g_system;
- int ptxinfo_lex(void);
- void ptxinfo_addinfo();
+ int ptxinfo_lex(YYSTYPE * yylval_param, yyscan_t yyscanner, ptxinfo_data* ptxinfo);
+ void yyerror(yyscan_t yyscanner, ptxinfo_data* ptxinfo, const char* msg);
void ptxinfo_function(const char *fname );
void ptxinfo_regs( unsigned nregs );
void ptxinfo_lmem( unsigned declared, unsigned system );
void ptxinfo_gmem( unsigned declared, unsigned system );
void ptxinfo_smem( unsigned declared, unsigned system );
void ptxinfo_cmem( unsigned nbytes, unsigned bank );
- int ptxinfo_error(const char*);
void ptxinfo_linenum( unsigned );
void ptxinfo_dup_type( const char* );
%}
@@ -93,7 +103,7 @@ line: HEADER INFO COLON line_info
;
line_info: function_name
- | function_info { ptxinfo_addinfo(); }
+ | function_info { ptxinfo->ptxinfo_addinfo(); }
| gmem_info
;
diff --git a/src/debug.cc b/src/debug.cc
index ae15760..c00ff9e 100644
--- a/src/debug.cc
+++ b/src/debug.cc
@@ -36,28 +36,7 @@
#include <stdio.h>
#include <string.h>
-class watchpoint_event {
-public:
- watchpoint_event()
- {
- m_thread=NULL;
- m_inst=NULL;
- }
- watchpoint_event(const ptx_thread_info *thd, const ptx_instruction *pI)
- {
- m_thread=thd;
- m_inst = pI;
- }
- const ptx_thread_info *thread() const { return m_thread; }
- const ptx_instruction *inst() const { return m_inst; }
-private:
- const ptx_thread_info *m_thread;
- const ptx_instruction *m_inst;
-};
-
-std::map<unsigned,watchpoint_event> g_watchpoint_hits;
-
-void hit_watchpoint( unsigned watchpoint_num, ptx_thread_info *thd, const ptx_instruction *pI )
+void gpgpu_sim::hit_watchpoint( unsigned watchpoint_num, ptx_thread_info *thd, const ptx_instruction *pI )
{
g_watchpoint_hits[watchpoint_num]=watchpoint_event(thd,pI);
}
diff --git a/src/debug.h b/src/debug.h
index 1277494..4e79a9f 100644
--- a/src/debug.h
+++ b/src/debug.h
@@ -83,11 +83,8 @@ private:
unsigned m_value;
};
-extern int gpgpu_ptx_instruction_classification ;
-
class ptx_thread_info;
class ptx_instruction;
bool thread_at_brkpt( ptx_thread_info *thd_info, const class brk_pt &b );
-void hit_watchpoint( unsigned watchpoint_num, ptx_thread_info *thd, const ptx_instruction *pI );
#endif
diff --git a/src/gpgpu-sim/Makefile b/src/gpgpu-sim/Makefile
index f10a8a4..4994577 100644
--- a/src/gpgpu-sim/Makefile
+++ b/src/gpgpu-sim/Makefile
@@ -53,6 +53,8 @@ else
CXXFLAGS +=
endif
+CXXFLAGS += -I$(CUDA_INSTALL_PATH)/include
+
POWER_FLAGS=
ifneq ($(GPGPUSIM_POWER_MODEL),)
POWER_FLAGS = -I$(GPGPUSIM_POWER_MODEL) -DGPGPUSIM_POWER_MODEL
diff --git a/src/gpgpu-sim/dram.cc b/src/gpgpu-sim/dram.cc
index 192cb65..d443d79 100644
--- a/src/gpgpu-sim/dram.cc
+++ b/src/gpgpu-sim/dram.cc
@@ -41,13 +41,14 @@ int PRINT_CYCLE = 0;
template class fifo_pipeline<mem_fetch>;
template class fifo_pipeline<dram_req_t>;
-dram_t::dram_t( unsigned int partition_id, const struct memory_config *config, memory_stats_t *stats,
- memory_partition_unit *mp )
+dram_t::dram_t( unsigned int partition_id, const memory_config *config, memory_stats_t *stats,
+ memory_partition_unit *mp, gpgpu_sim* gpu )
{
id = partition_id;
m_memory_partition_unit = mp;
m_stats = stats;
m_config = config;
+ m_gpu = gpu;
//rowblp
access_num=0;
@@ -191,11 +192,12 @@ unsigned int dram_t::queue_limit() const
}
-dram_req_t::dram_req_t( class mem_fetch *mf, unsigned banks, unsigned dram_bnk_indexing_policy)
+dram_req_t::dram_req_t( class mem_fetch *mf, unsigned banks, unsigned dram_bnk_indexing_policy, class gpgpu_sim* gpu)
{
txbytes = 0;
dqbytes = 0;
data = mf;
+ m_gpu = gpu;
const addrdec_t &tlx = mf->get_tlx_addr();
@@ -226,9 +228,9 @@ dram_req_t::dram_req_t( class mem_fetch *mf, unsigned banks, unsigned dram_bnk_i
col = tlx.col;
nbytes = mf->get_data_size();
- timestamp = gpu_tot_sim_cycle + gpu_sim_cycle;
+ timestamp = m_gpu->gpu_tot_sim_cycle + m_gpu->gpu_sim_cycle;
addr = mf->get_addr();
- insertion_time = (unsigned) gpu_sim_cycle;
+ insertion_time = (unsigned) m_gpu->gpu_sim_cycle;
rw = data->get_is_write()?WRITE:READ;
}
@@ -236,9 +238,9 @@ void dram_t::push( class mem_fetch *data )
{
assert(id == data->get_tlx_addr().chip); // Ensure request is in correct memory partition
- dram_req_t *mrq = new dram_req_t(data,m_config->nbk,m_config->dram_bnk_indexing_policy);
+ dram_req_t *mrq = new dram_req_t(data,m_config->nbk,m_config->dram_bnk_indexing_policy,m_memory_partition_unit->get_mgpu());
- data->set_status(IN_PARTITION_MC_INTERFACE_QUEUE,gpu_sim_cycle+gpu_tot_sim_cycle);
+ data->set_status(IN_PARTITION_MC_INTERFACE_QUEUE,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
mrqq->push(mrq);
// stats...
@@ -259,7 +261,7 @@ void dram_t::scheduler_fifo()
if (!mrqq->empty()) {
unsigned int bkn;
dram_req_t *head_mrqq = mrqq->top();
- head_mrqq->data->set_status(IN_PARTITION_MC_BANK_ARB_QUEUE,gpu_sim_cycle+gpu_tot_sim_cycle);
+ head_mrqq->data->set_status(IN_PARTITION_MC_BANK_ARB_QUEUE,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
bkn = head_mrqq->bk;
if (!bk[bkn]->mrq)
bk[bkn]->mrq = mrqq->pop();
@@ -283,7 +285,7 @@ void dram_t::cycle()
if (cmd->dqbytes >= cmd->nbytes) {
mem_fetch *data = cmd->data;
- data->set_status(IN_PARTITION_MC_RETURNQ,gpu_sim_cycle+gpu_tot_sim_cycle);
+ data->set_status(IN_PARTITION_MC_RETURNQ,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
if( data->get_access_type() != L1_WRBK_ACC && data->get_access_type() != L2_WRBK_ACC ) {
data->set_reply();
returnq->push(data);
@@ -566,7 +568,7 @@ bool dram_t::issue_col_command(int j)
bool issued = false;
unsigned grp = get_bankgrp_number(j);
if (bk[j]->mrq) { //if currently servicing a memory request
- bk[j]->mrq->data->set_status(IN_PARTITION_DRAM,gpu_sim_cycle+gpu_tot_sim_cycle);
+ bk[j]->mrq->data->set_status(IN_PARTITION_DRAM,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
// correct row activated for a READ
if ( !issued && !CCDc && !bk[j]->RCDc &&
!(bkgrp[grp]->CCDLc) &&
@@ -654,7 +656,7 @@ bool dram_t::issue_row_command(int j)
bool issued = false;
unsigned grp = get_bankgrp_number(j);
if (bk[j]->mrq) { //if currently servicing a memory request
- bk[j]->mrq->data->set_status(IN_PARTITION_DRAM,gpu_sim_cycle+gpu_tot_sim_cycle);
+ bk[j]->mrq->data->set_status(IN_PARTITION_DRAM,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
// bank is idle
//else
if ( !issued && !RRDc &&
diff --git a/src/gpgpu-sim/dram.h b/src/gpgpu-sim/dram.h
index 1ab0153..0bd9725 100644
--- a/src/gpgpu-sim/dram.h
+++ b/src/gpgpu-sim/dram.h
@@ -48,7 +48,7 @@
class dram_req_t {
public:
- dram_req_t( class mem_fetch *data , unsigned banks, unsigned dram_bnk_indexing_policy);
+ dram_req_t( class mem_fetch *data , unsigned banks, unsigned dram_bnk_indexing_policy, class gpgpu_sim* gpu);
unsigned int row;
unsigned int col;
@@ -62,6 +62,7 @@ public:
unsigned long long int addr;
unsigned int insertion_time;
class mem_fetch * data;
+ class gpgpu_sim * m_gpu;
};
struct bankgrp_t
@@ -105,12 +106,13 @@ enum bank_grp_bits_position{
};
class mem_fetch;
+class memory_config;
class dram_t
{
public:
- dram_t( unsigned int parition_id, const struct memory_config *config, class memory_stats_t *stats,
- class memory_partition_unit *mp );
+ dram_t( unsigned int parition_id, const memory_config *config, class memory_stats_t *stats,
+ class memory_partition_unit *mp, class gpgpu_sim* gpu );
bool full(bool is_write) const;
void print( FILE* simFile ) const;
@@ -129,6 +131,7 @@ public:
void dram_log (int task);
class memory_partition_unit *m_memory_partition_unit;
+ class gpgpu_sim* m_gpu;
unsigned int id;
// Power Model
@@ -143,7 +146,7 @@ public:
- const struct memory_config *m_config;
+ const memory_config *m_config;
private:
bankgrp_t **bkgrp;
diff --git a/src/gpgpu-sim/dram_sched.cc b/src/gpgpu-sim/dram_sched.cc
index ff50050..6ee6271 100644
--- a/src/gpgpu-sim/dram_sched.cc
+++ b/src/gpgpu-sim/dram_sched.cc
@@ -84,13 +84,13 @@ void frfcfs_scheduler::add_req( dram_req_t *req )
void frfcfs_scheduler::data_collection(unsigned int bank)
{
- if (gpu_sim_cycle > row_service_timestamp[bank]) {
- curr_row_service_time[bank] = gpu_sim_cycle - row_service_timestamp[bank];
+ if (m_dram->m_gpu->gpu_sim_cycle > row_service_timestamp[bank]) {
+ curr_row_service_time[bank] = m_dram->m_gpu->gpu_sim_cycle - row_service_timestamp[bank];
if (curr_row_service_time[bank] > m_stats->max_servicetime2samerow[m_dram->id][bank])
m_stats->max_servicetime2samerow[m_dram->id][bank] = curr_row_service_time[bank];
}
curr_row_service_time[bank] = 0;
- row_service_timestamp[bank] = gpu_sim_cycle;
+ row_service_timestamp[bank] = m_dram->m_gpu->gpu_sim_cycle;
if (m_stats->concurrent_row_access[m_dram->id][bank] > m_stats->max_conc_access2samerow[m_dram->id][bank]) {
m_stats->max_conc_access2samerow[m_dram->id][bank] = m_stats->concurrent_row_access[m_dram->id][bank];
}
@@ -215,7 +215,7 @@ void dram_t::scheduler_frfcfs()
m_stats->total_n_reads++;
}
- req->data->set_status(IN_PARTITION_MC_INPUT_QUEUE,gpu_sim_cycle+gpu_tot_sim_cycle);
+ req->data->set_status(IN_PARTITION_MC_INPUT_QUEUE,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
sched->add_req(req);
}
@@ -228,14 +228,14 @@ void dram_t::scheduler_frfcfs()
req = sched->schedule(b, bk[b]->curr_row);
if ( req ) {
- req->data->set_status(IN_PARTITION_MC_BANK_ARB_QUEUE,gpu_sim_cycle+gpu_tot_sim_cycle);
+ req->data->set_status(IN_PARTITION_MC_BANK_ARB_QUEUE,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
prio = (prio+1)%m_config->nbk;
bk[b]->mrq = req;
if (m_config->gpgpu_memlatency_stat) {
- mrq_latency = gpu_sim_cycle + gpu_tot_sim_cycle - bk[b]->mrq->timestamp;
+ mrq_latency = m_gpu->gpu_sim_cycle + m_gpu->gpu_tot_sim_cycle - bk[b]->mrq->timestamp;
m_stats->tot_mrq_latency += mrq_latency;
m_stats->tot_mrq_num++;
- bk[b]->mrq->timestamp = gpu_tot_sim_cycle + gpu_sim_cycle;
+ bk[b]->mrq->timestamp =m_gpu->gpu_tot_sim_cycle + m_gpu->gpu_sim_cycle;
m_stats->mrq_lat_table[LOGB2(mrq_latency)]++;
if (mrq_latency > m_stats->max_mrq_latency) {
m_stats->max_mrq_latency = mrq_latency;
diff --git a/src/gpgpu-sim/gpu-cache.cc b/src/gpgpu-sim/gpu-cache.cc
index 370f6e6..1705821 100644
--- a/src/gpgpu-sim/gpu-cache.cc
+++ b/src/gpgpu-sim/gpu-cache.cc
@@ -26,6 +26,7 @@
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#include "gpu-cache.h"
+#include "gpu-sim.h"
#include "stat-tool.h"
#include <assert.h>
@@ -1250,7 +1251,8 @@ data_cache::wr_miss_wa_naive( new_addr_type addr,
false, // Now performing a read
mf->get_access_warp_mask(),
mf->get_access_byte_mask(),
- mf->get_access_sector_mask());
+ mf->get_access_sector_mask(),
+ m_gpu->gpgpu_ctx);
mem_fetch *n_mf = new mem_fetch( *ma,
NULL,
@@ -1258,7 +1260,8 @@ data_cache::wr_miss_wa_naive( new_addr_type addr,
mf->get_wid(),
mf->get_sid(),
mf->get_tpc(),
- mf->get_mem_config());
+ mf->get_mem_config(),
+ m_gpu->gpu_tot_sim_cycle+m_gpu->gpu_sim_cycle);
bool do_miss = false;
bool wb = false;
@@ -1276,7 +1279,7 @@ data_cache::wr_miss_wa_naive( new_addr_type addr,
if( wb && (m_config.m_write_policy != WRITE_THROUGH) ) {
assert(status == MISS); //SECTOR_MISS and HIT_RESERVED should not send write back
mem_fetch *wb = m_memfetch_creator->alloc(evicted.m_block_addr,
- m_wrbk_type,evicted.m_modified_size,true);
+ m_wrbk_type,evicted.m_modified_size,true,m_gpu->gpu_tot_sim_cycle+m_gpu->gpu_sim_cycle);
send_write_request(wb, cache_event(WRITE_BACK_REQUEST_SENT, evicted), time, events);
}
return MISS;
@@ -1320,7 +1323,7 @@ data_cache::wr_miss_wa_fetch_on_write( new_addr_type addr,
// (already modified lower level)
if( wb && (m_config.m_write_policy != WRITE_THROUGH) ) {
mem_fetch *wb = m_memfetch_creator->alloc(evicted.m_block_addr,
- m_wrbk_type,evicted.m_modified_size,true);
+ m_wrbk_type,evicted.m_modified_size,true,m_gpu->gpu_tot_sim_cycle+m_gpu->gpu_sim_cycle);
send_write_request(wb, cache_event(WRITE_BACK_REQUEST_SENT, evicted), time, events);
}
return MISS;
@@ -1363,7 +1366,8 @@ data_cache::wr_miss_wa_fetch_on_write( new_addr_type addr,
false, // Now performing a read
mf->get_access_warp_mask(),
mf->get_access_byte_mask(),
- mf->get_access_sector_mask());
+ mf->get_access_sector_mask(),
+ m_gpu->gpgpu_ctx);
mem_fetch *n_mf = new mem_fetch( *ma,
NULL,
@@ -1372,6 +1376,7 @@ data_cache::wr_miss_wa_fetch_on_write( new_addr_type addr,
mf->get_sid(),
mf->get_tpc(),
mf->get_mem_config(),
+ m_gpu->gpu_tot_sim_cycle+m_gpu->gpu_sim_cycle,
NULL,
mf);
@@ -1395,7 +1400,7 @@ data_cache::wr_miss_wa_fetch_on_write( new_addr_type addr,
// (already modified lower level)
if(wb && (m_config.m_write_policy != WRITE_THROUGH) ){
mem_fetch *wb = m_memfetch_creator->alloc(evicted.m_block_addr,
- m_wrbk_type,evicted.m_modified_size,true);
+ m_wrbk_type,evicted.m_modified_size,true,m_gpu->gpu_tot_sim_cycle+m_gpu->gpu_sim_cycle);
send_write_request(wb, cache_event(WRITE_BACK_REQUEST_SENT, evicted), time, events);
}
return MISS;
@@ -1448,7 +1453,7 @@ data_cache::wr_miss_wa_lazy_fetch_on_read( new_addr_type addr,
// (already modified lower level)
if( wb && (m_config.m_write_policy != WRITE_THROUGH) ) {
mem_fetch *wb = m_memfetch_creator->alloc(evicted.m_block_addr,
- m_wrbk_type,evicted.m_modified_size,true);
+ m_wrbk_type,evicted.m_modified_size,true,m_gpu->gpu_tot_sim_cycle+m_gpu->gpu_sim_cycle);
send_write_request(wb, cache_event(WRITE_BACK_REQUEST_SENT, evicted), time, events);
}
return MISS;
@@ -1533,7 +1538,7 @@ data_cache::rd_miss_base( new_addr_type addr,
// (already modified lower level)
if(wb && (m_config.m_write_policy != WRITE_THROUGH) ){
mem_fetch *wb = m_memfetch_creator->alloc(evicted.m_block_addr,
- m_wrbk_type,evicted.m_modified_size,true);
+ m_wrbk_type,evicted.m_modified_size,true,m_gpu->gpu_tot_sim_cycle+m_gpu->gpu_sim_cycle);
send_write_request(wb, WRITE_BACK_REQUEST_SENT, time, events);
}
return MISS;
diff --git a/src/gpgpu-sim/gpu-cache.h b/src/gpgpu-sim/gpu-cache.h
index 337f710..be33d96 100644
--- a/src/gpgpu-sim/gpu-cache.h
+++ b/src/gpgpu-sim/gpu-cache.h
@@ -1290,12 +1290,13 @@ public:
data_cache( const char *name, cache_config &config,
int core_id, int type_id, mem_fetch_interface *memport,
mem_fetch_allocator *mfcreator, enum mem_fetch_status status,
- mem_access_type wr_alloc_type, mem_access_type wrbk_type )
+ mem_access_type wr_alloc_type, mem_access_type wrbk_type, class gpgpu_sim* gpu )
: baseline_cache(name,config,core_id,type_id,memport,status)
{
init( mfcreator );
m_wr_alloc_type = wr_alloc_type;
m_wrbk_type = wrbk_type;
+ m_gpu=gpu;
}
virtual ~data_cache() {}
@@ -1353,16 +1354,19 @@ protected:
enum mem_fetch_status status,
tag_array* new_tag_array,
mem_access_type wr_alloc_type,
- mem_access_type wrbk_type)
+ mem_access_type wrbk_type,
+ class gpgpu_sim* gpu )
: baseline_cache(name, config, core_id, type_id, memport,status, new_tag_array)
{
init( mfcreator );
m_wr_alloc_type = wr_alloc_type;
m_wrbk_type = wrbk_type;
+ m_gpu=gpu;
}
mem_access_type m_wr_alloc_type; // Specifies type of write allocate request (e.g., L1 or L2)
mem_access_type m_wrbk_type; // Specifies type of writeback request (e.g., L1 or L2)
+ class gpgpu_sim* m_gpu;
//! A general function that takes the result of a tag_array probe
// and performs the correspding functions based on the cache configuration
@@ -1519,8 +1523,8 @@ class l1_cache : public data_cache {
public:
l1_cache(const char *name, cache_config &config,
int core_id, int type_id, mem_fetch_interface *memport,
- mem_fetch_allocator *mfcreator, enum mem_fetch_status status )
- : data_cache(name,config,core_id,type_id,memport,mfcreator,status, L1_WR_ALLOC_R, L1_WRBK_ACC){}
+ mem_fetch_allocator *mfcreator, enum mem_fetch_status status, class gpgpu_sim* gpu )
+ : data_cache(name,config,core_id,type_id,memport,mfcreator,status, L1_WR_ALLOC_R, L1_WRBK_ACC, gpu){}
virtual ~l1_cache(){}
@@ -1538,10 +1542,11 @@ protected:
mem_fetch_interface *memport,
mem_fetch_allocator *mfcreator,
enum mem_fetch_status status,
- tag_array* new_tag_array )
+ tag_array* new_tag_array,
+ class gpgpu_sim* gpu)
: data_cache( name,
config,
- core_id,type_id,memport,mfcreator,status, new_tag_array, L1_WR_ALLOC_R, L1_WRBK_ACC ){}
+ core_id,type_id,memport,mfcreator,status, new_tag_array, L1_WR_ALLOC_R, L1_WRBK_ACC, gpu ){}
};
@@ -1551,8 +1556,8 @@ class l2_cache : public data_cache {
public:
l2_cache(const char *name, cache_config &config,
int core_id, int type_id, mem_fetch_interface *memport,
- mem_fetch_allocator *mfcreator, enum mem_fetch_status status )
- : data_cache(name,config,core_id,type_id,memport,mfcreator,status, L2_WR_ALLOC_R, L2_WRBK_ACC){}
+ mem_fetch_allocator *mfcreator, enum mem_fetch_status status, class gpgpu_sim* gpu )
+ : data_cache(name,config,core_id,type_id,memport,mfcreator,status, L2_WR_ALLOC_R, L2_WRBK_ACC, gpu){}
virtual ~l2_cache() {}
diff --git a/src/gpgpu-sim/gpu-sim.cc b/src/gpgpu-sim/gpu-sim.cc
index 92d5366..622b8bd 100644
--- a/src/gpgpu-sim/gpu-sim.cc
+++ b/src/gpgpu-sim/gpu-sim.cc
@@ -65,6 +65,7 @@
#include "visualizer.h"
#include "stats.h"
#include "../cuda-sim/cuda_device_runtime.h"
+#include "../../libcuda/gpgpu_context.h"
#ifdef GPGPUSIM_POWER_MODEL
#include "power_interface.h"
@@ -83,23 +84,6 @@ class gpgpu_sim_wrapper {};
bool g_interactive_debugger_enabled=false;
-unsigned long long gpu_sim_cycle = 0;
-unsigned long long gpu_tot_sim_cycle = 0;
-unsigned long long elapsed_cycles_sm_tot = 0; //this is a equivalent metric generated as nvprof. that only counts when SM is active
-
-
-// performance counter for stalls due to congestion.
-unsigned int gpu_stall_dramfull = 0;
-unsigned int gpu_stall_icnt2sh = 0;
-unsigned long long partiton_reqs_in_parallel = 0;
-unsigned long long partiton_reqs_in_parallel_total = 0;
-unsigned long long partiton_reqs_in_parallel_util = 0;
-unsigned long long partiton_reqs_in_parallel_util_total = 0;
-unsigned long long gpu_sim_cycle_parition_util = 0;
-unsigned long long gpu_tot_sim_cycle_parition_util = 0;
-unsigned long long partiton_replys_in_parallel = 0;
-unsigned long long partiton_replys_in_parallel_total = 0;
-
tr1_hash_map<new_addr_type,unsigned> address_random_interleaving;
/* Clock Domains */
@@ -113,8 +97,6 @@ tr1_hash_map<new_addr_type,unsigned> address_random_interleaving;
#define MEM_LATENCY_STAT_IMPL
-
-
#include "mem_latency_stat.h"
void power_config::reg_options(class OptionParser * opp)
@@ -520,11 +502,11 @@ void gpgpu_sim_config::reg_options(option_parser_t opp)
option_parser_register(opp, "-gpgpu_deadlock_detect", OPT_BOOL, &gpu_deadlock_detect,
"Stop the simulation at deadlock (1=on (default), 0=off)",
"1");
- option_parser_register(opp, "-gpgpu_ptx_instruction_classification", OPT_INT32,
- &gpgpu_ptx_instruction_classification,
+ option_parser_register(opp, "-gpgpu_ptx_instruction_classification", OPT_INT32,
+ &(gpgpu_ctx->func_sim->gpgpu_ptx_instruction_classification),
"if enabled will classify ptx instruction types per kernel (Max 255 kernels now)",
"0");
- option_parser_register(opp, "-gpgpu_ptx_sim_mode", OPT_INT32, &g_ptx_sim_mode,
+ option_parser_register(opp, "-gpgpu_ptx_sim_mode", OPT_INT32, &(gpgpu_ctx->func_sim->g_ptx_sim_mode),
"Select between Performance (default) or Functional simulation (1)",
"0");
option_parser_register(opp, "-gpgpu_clock_domains", OPT_CSTR, &gpgpu_clock_domains,
@@ -566,16 +548,14 @@ void gpgpu_sim_config::reg_options(option_parser_t opp)
option_parser_register(opp, "-trace_sampling_memory_partition", OPT_INT32,
&Trace::sampling_memory_partition, "The memory partition which is printed using MEMPART_DPRINTF. Default -1 (i.e. all)",
"-1");
- ptx_file_line_stats_options(opp);
+ gpgpu_ctx->stats->ptx_file_line_stats_options(opp);
//Jin: kernel launch latency
- extern unsigned g_kernel_launch_latency;
option_parser_register(opp, "-gpgpu_kernel_launch_latency", OPT_INT32,
- &g_kernel_launch_latency, "Kernel launch latency in cycles. Default: 0",
+ &(gpgpu_ctx->device_runtime->g_kernel_launch_latency), "Kernel launch latency in cycles. Default: 0",
"0");
- extern bool g_cdp_enabled;
option_parser_register(opp, "-gpgpu_cdp_enabled", OPT_BOOL,
- &g_cdp_enabled, "Turn on CDP",
+ &(gpgpu_ctx->device_runtime->g_cdp_enabled), "Turn on CDP",
"0");
}
@@ -719,14 +699,13 @@ void gpgpu_sim::stop_all_running_kernels(){
}
}
-void set_ptx_warp_size(const struct core_config * warp_size);
-
-gpgpu_sim::gpgpu_sim( const gpgpu_sim_config &config )
- : gpgpu_t(config), m_config(config)
-{
+gpgpu_sim::gpgpu_sim( const gpgpu_sim_config &config, gpgpu_context* ctx )
+ : gpgpu_t(config, ctx), m_config(config)
+{
+ gpgpu_ctx = ctx;
m_shader_config = &m_config.m_shader_config;
m_memory_config = &m_config.m_memory_config;
- set_ptx_warp_size(m_shader_config);
+ ctx->ptx_parser->set_ptx_warp_size(m_shader_config);
ptx_file_line_stats_create_exposed_latency_tracker(m_config.num_shader());
#ifdef GPGPUSIM_POWER_MODEL
@@ -734,7 +713,7 @@ gpgpu_sim::gpgpu_sim( const gpgpu_sim_config &config )
#endif
m_shader_stats = new shader_core_stats(m_shader_config);
- m_memory_stats = new memory_stats_t(m_config.num_shader(),m_shader_config,m_memory_config);
+ m_memory_stats = new memory_stats_t(m_config.num_shader(),m_shader_config,m_memory_config,this);
average_pipeline_duty_cycle = (float *)malloc(sizeof(float));
active_sms=(float *)malloc(sizeof(float));
m_power_stats = new power_stat_t(m_shader_config,average_pipeline_duty_cycle,active_sms,m_shader_stats,m_memory_config,m_memory_stats);
@@ -745,6 +724,16 @@ gpgpu_sim::gpgpu_sim( const gpgpu_sim_config &config )
m_total_cta_launched = 0;
gpu_deadlock = false;
+ gpu_stall_dramfull = 0;
+ gpu_stall_icnt2sh = 0;
+ partiton_reqs_in_parallel = 0;
+ partiton_reqs_in_parallel_total = 0;
+ partiton_reqs_in_parallel_util = 0;
+ partiton_reqs_in_parallel_util_total = 0;
+ gpu_sim_cycle_parition_util = 0;
+ gpu_tot_sim_cycle_parition_util = 0;
+ partiton_replys_in_parallel = 0;
+ partiton_replys_in_parallel_total = 0;
m_cluster = new simt_core_cluster*[m_shader_config->n_simt_clusters];
for (unsigned i=0;i<m_shader_config->n_simt_clusters;i++)
@@ -753,7 +742,7 @@ gpgpu_sim::gpgpu_sim( const gpgpu_sim_config &config )
m_memory_partition_unit = new memory_partition_unit*[m_memory_config->m_n_mem];
m_memory_sub_partition = new memory_sub_partition*[m_memory_config->m_n_mem_sub_partition];
for (unsigned i=0;i<m_memory_config->m_n_mem;i++) {
- m_memory_partition_unit[i] = new memory_partition_unit(i, m_memory_config, m_memory_stats);
+ m_memory_partition_unit[i] = new memory_partition_unit(i, m_memory_config, m_memory_stats, this);
for (unsigned p = 0; p < m_memory_config->m_n_sub_partition_per_memory_channel; p++) {
unsigned submpid = i * m_memory_config->m_n_sub_partition_per_memory_channel + p;
m_memory_sub_partition[submpid] = m_memory_partition_unit[i]->get_sub_partition(p);
@@ -904,13 +893,13 @@ void gpgpu_sim::init()
gpu_sim_cycle_parition_util = 0;
reinit_clock_domains();
- set_param_gpgpu_num_shaders(m_config.num_shader());
+ gpgpu_ctx->func_sim->set_param_gpgpu_num_shaders(m_config.num_shader());
for (unsigned i=0;i<m_shader_config->n_simt_clusters;i++)
m_cluster[i]->reinit();
m_shader_stats->new_grid();
// initialize the control-flow, memory access, memory latency logger
if (m_config.g_visualizer_enabled) {
- create_thread_CFlogger( m_config.num_shader(), m_shader_config->n_thread_per_shader, 0, m_config.gpgpu_cflog_interval );
+ create_thread_CFlogger( gpgpu_ctx, m_config.num_shader(), m_shader_config->n_thread_per_shader, 0, m_config.gpgpu_cflog_interval );
}
shader_CTA_count_create( m_config.num_shader(), m_config.gpgpu_cflog_interval);
if (m_config.gpgpu_cflog_interval != 0) {
@@ -956,7 +945,7 @@ void gpgpu_sim::update_stats() {
void gpgpu_sim::print_stats()
{
- ptx_file_line_stats_write_file();
+ gpgpu_ctx->stats->ptx_file_line_stats_write_file();
gpu_print_stat();
if (g_network_mode) {
@@ -1122,7 +1111,6 @@ void gpgpu_sim::gpu_print_stat()
printf("gpu_sim_insn = %lld\n", gpu_sim_insn);
printf("gpu_ipc = %12.4f\n", (float)gpu_sim_insn / gpu_sim_cycle);
printf("gpu_tot_sim_cycle = %lld\n", gpu_tot_sim_cycle+gpu_sim_cycle);
- printf("elapsed_cycles_sm_tot = %lld\n", elapsed_cycles_sm_tot);
printf("gpu_tot_sim_insn = %lld\n", gpu_tot_sim_insn+gpu_sim_insn);
printf("gpu_tot_ipc = %12.4f\n", (float)(gpu_tot_sim_insn+gpu_sim_insn) / (gpu_tot_sim_cycle+gpu_sim_cycle));
printf("gpu_tot_issued_cta = %lld\n", gpu_tot_issued_cta + m_total_cta_launched);
@@ -1130,8 +1118,7 @@ void gpgpu_sim::gpu_print_stat()
printf("gpu_tot_occupancy = %.4f\% \n", (gpu_occupancy + gpu_tot_occupancy).get_occ_fraction() * 100);
- extern unsigned long long g_max_total_param_size;
- fprintf(statfout, "max_total_param_size = %llu\n", g_max_total_param_size);
+ fprintf(statfout, "max_total_param_size = %llu\n", gpgpu_ctx->device_runtime->g_max_total_param_size);
// performance counter for stalls due to congestion.
printf("gpu_stall_dramfull = %d\n", gpu_stall_dramfull);
@@ -1154,7 +1141,7 @@ void gpgpu_sim::gpu_print_stat()
time_t curr_time;
time(&curr_time);
- unsigned long long elapsed_time = MAX( curr_time - g_simulation_starttime, 1 );
+ unsigned long long elapsed_time = MAX( curr_time - GPGPUsim_ctx_ptr()->g_simulation_starttime, 1 );
printf( "gpu_total_sim_rate=%u\n", (unsigned)( ( gpu_tot_sim_insn + gpu_sim_insn ) / elapsed_time ) );
//shader_print_l1_miss_stat( stdout );
@@ -1223,9 +1210,9 @@ void gpgpu_sim::gpu_print_stat()
spill_log_to_file (stdout, 1, gpu_sim_cycle);
insn_warp_occ_print(stdout);
}
- if ( gpgpu_ptx_instruction_classification ) {
- StatDisp( g_inst_classification_stat[g_ptx_kernel_count]);
- StatDisp( g_inst_op_classification_stat[g_ptx_kernel_count]);
+ if ( gpgpu_ctx->func_sim->gpgpu_ptx_instruction_classification ) {
+ StatDisp( gpgpu_ctx->func_sim->g_inst_classification_stat[gpgpu_ctx->func_sim->g_ptx_kernel_count]);
+ StatDisp( gpgpu_ctx->func_sim->g_inst_op_classification_stat[gpgpu_ctx->func_sim->g_ptx_kernel_count]);
}
#ifdef GPGPUSIM_POWER_MODEL
@@ -1518,7 +1505,7 @@ void shader_core_ctx::issue_block2core( kernel_info_t &kernel )
shader_CTA_count_log(m_sid, 1);
SHADER_DPRINTF(LIVENESS, "GPGPU-Sim uArch: cta:%2u, start_tid:%4u, end_tid:%4u, initialized @(%lld,%lld)\n",
- free_cta_hw_id, start_thread, end_thread, gpu_sim_cycle, gpu_tot_sim_cycle );
+ free_cta_hw_id, start_thread, end_thread, m_gpu->gpu_sim_cycle, m_gpu->gpu_tot_sim_cycle );
}
@@ -1727,7 +1714,7 @@ void gpgpu_sim::cycle()
time_t days, hrs, minutes, sec;
time_t curr_time;
time(&curr_time);
- unsigned long long elapsed_time = MAX(curr_time - g_simulation_starttime, 1);
+ unsigned long long elapsed_time = MAX(curr_time - GPGPUsim_ctx_ptr()->g_simulation_starttime, 1);
if ( (elapsed_time - last_liveness_message_time) >= m_config.liveness_message_freq && DTRACE(LIVENESS) ) {
days = elapsed_time/(3600*24);
hrs = elapsed_time/3600 - 24*days;
@@ -1738,7 +1725,7 @@ void gpgpu_sim::cycle()
for (unsigned i=0;i<m_shader_config->n_simt_clusters;i++) {
m_cluster[i]->get_current_occupancy(active, total);
}
- DPRINTF(LIVENESS, "uArch: inst.: %lld (ipc=%4.1f, occ=%0.4f\% [%llu / %llu]) sim_rate=%u (inst/sec) elapsed = %u:%u:%02u:%02u / %s",
+ DPRINTFG(LIVENESS, "uArch: inst.: %lld (ipc=%4.1f, occ=%0.4f\% [%llu / %llu]) sim_rate=%u (inst/sec) elapsed = %u:%u:%02u:%02u / %s",
gpu_tot_sim_insn + gpu_sim_insn,
(double)gpu_sim_insn/(double)gpu_sim_cycle,
float(active)/float(total) * 100, active, total,
@@ -1779,7 +1766,7 @@ void gpgpu_sim::cycle()
#if (CUDART_VERSION >= 5000)
//launch device kernel
- launch_one_device_kernel();
+ gpgpu_ctx->device_runtime->launch_one_device_kernel();
#endif
}
}
@@ -1852,12 +1839,12 @@ void gpgpu_sim::dump_pipeline( int mask, int s, int m ) const
fflush(stdout);
}
-const struct shader_core_config * gpgpu_sim::getShaderCoreConfig()
+const shader_core_config * gpgpu_sim::getShaderCoreConfig()
{
return m_shader_config;
}
-const struct memory_config * gpgpu_sim::getMemoryConfig()
+const memory_config * gpgpu_sim::getMemoryConfig()
{
return m_memory_config;
}
diff --git a/src/gpgpu-sim/gpu-sim.h b/src/gpgpu-sim/gpu-sim.h
index c14d0a7..f841bf9 100644
--- a/src/gpgpu-sim/gpu-sim.h
+++ b/src/gpgpu-sim/gpu-sim.h
@@ -33,6 +33,7 @@
#include "../trace.h"
#include "addrdec.h"
#include "shader.h"
+#include "gpu-cache.h"
#include <iostream>
#include <fstream>
#include <list>
@@ -62,8 +63,9 @@
#define SAMPLELOG 222
#define DUMPLOG 333
-extern tr1_hash_map<new_addr_type,unsigned> address_random_interleaving;
+class gpgpu_context;
+extern tr1_hash_map<new_addr_type,unsigned> address_random_interleaving;
enum dram_ctrl_t {
DRAM_FIFO=0,
@@ -142,13 +144,14 @@ struct power_config {
};
-
-struct memory_config {
- memory_config()
+class memory_config {
+ public:
+ memory_config(gpgpu_context* ctx)
{
m_valid = false;
gpgpu_dram_timing_opt=NULL;
gpgpu_L2_queue_config=NULL;
+ gpgpu_ctx = ctx;
}
void init()
{
@@ -291,17 +294,22 @@ struct memory_config {
unsigned write_low_watermark;
bool m_perf_sim_memcpy;
bool simple_dram_model;
+
+ gpgpu_context* gpgpu_ctx;
};
// global counters and flags (please try not to add to this list!!!)
extern unsigned long long gpu_sim_cycle;
extern unsigned long long gpu_tot_sim_cycle;
-extern unsigned long long elapsed_cycles_sm_tot;
+
extern bool g_interactive_debugger_enabled;
class gpgpu_sim_config : public power_config, public gpgpu_functional_sim_config {
public:
- gpgpu_sim_config() { m_valid = false; }
+ gpgpu_sim_config(gpgpu_context* ctx): m_shader_config(ctx), m_memory_config(ctx) {
+ m_valid = false;
+ gpgpu_ctx = ctx;
+ }
void reg_options(class OptionParser * opp);
void init()
{
@@ -347,6 +355,8 @@ private:
void init_clock_domains(void );
+ // backward pointer
+ class gpgpu_context* gpgpu_ctx;
bool m_valid;
shader_core_config m_shader_config;
memory_config m_memory_config;
@@ -422,10 +432,31 @@ struct occupancy_stats {
}
};
+class gpgpu_context;
+class ptx_instruction;
+
+class watchpoint_event {
+public:
+ watchpoint_event()
+ {
+ m_thread=NULL;
+ m_inst=NULL;
+ }
+ watchpoint_event(const ptx_thread_info *thd, const ptx_instruction *pI)
+ {
+ m_thread=thd;
+ m_inst = pI;
+ }
+ const ptx_thread_info *thread() const { return m_thread; }
+ const ptx_instruction *inst() const { return m_inst; }
+private:
+ const ptx_thread_info *m_thread;
+ const ptx_instruction *m_inst;
+};
class gpgpu_sim : public gpgpu_t {
public:
- gpgpu_sim( const gpgpu_sim_config &config );
+ gpgpu_sim( const gpgpu_sim_config &config, gpgpu_context* ctx );
void set_prop( struct cudaDeviceProp *prop );
@@ -480,14 +511,14 @@ public:
/*!
* Returning the configuration of the shader core, used by the functional simulation only so far
*/
- const struct shader_core_config * getShaderCoreConfig();
+ const shader_core_config * getShaderCoreConfig();
//! Get shader core Memory Configuration
/*!
* Returning the memory configuration of the shader core, used by the functional simulation only so far
*/
- const struct memory_config * getMemoryConfig();
+ const memory_config * getMemoryConfig();
//! Get shader core SIMT cluster
@@ -496,6 +527,10 @@ public:
*/
simt_core_cluster * getSIMTCluster();
+ void hit_watchpoint( unsigned watchpoint_num, ptx_thread_info *thd, const ptx_instruction *pI );
+
+ // backward pointer
+ class gpgpu_context* gpgpu_ctx;
private:
// clocks
@@ -542,8 +577,8 @@ private:
const gpgpu_sim_config &m_config;
const struct cudaDeviceProp *m_cuda_properties;
- const struct shader_core_config *m_shader_config;
- const struct memory_config *m_memory_config;
+ const shader_core_config *m_shader_config;
+ const memory_config *m_memory_config;
// stats
class shader_core_stats *m_shader_stats;
@@ -558,6 +593,8 @@ private:
std::vector<std::string> m_executed_kernel_names; //< names of kernel for stat printout
std::vector<unsigned> m_executed_kernel_uids; //< uids of kernel launches for stat printout
+ std::map<unsigned,watchpoint_event> g_watchpoint_hits;
+
std::string executed_kernel_info_string(); //< format the kernel information into a string for stat printout
void clear_executed_kernel_info(); //< clear the kernel information after stat printout
@@ -570,6 +607,18 @@ public:
occupancy_stats gpu_occupancy;
occupancy_stats gpu_tot_occupancy;
+ // performance counter for stalls due to congestion.
+ unsigned int gpu_stall_dramfull;
+ unsigned int gpu_stall_icnt2sh;
+ unsigned long long partiton_reqs_in_parallel;
+ unsigned long long partiton_reqs_in_parallel_total;
+ unsigned long long partiton_reqs_in_parallel_util;
+ unsigned long long partiton_reqs_in_parallel_util_total;
+ unsigned long long gpu_sim_cycle_parition_util;
+ unsigned long long gpu_tot_sim_cycle_parition_util;
+ unsigned long long partiton_replys_in_parallel;
+ unsigned long long partiton_replys_in_parallel_total;
+
FuncCache get_cache_config(std::string kernel_name);
void set_cache_config(std::string kernel_name, FuncCache cacheConfig );
diff --git a/src/gpgpu-sim/l2cache.cc b/src/gpgpu-sim/l2cache.cc
index f24a596..f1672f9 100644
--- a/src/gpgpu-sim/l2cache.cc
+++ b/src/gpgpu-sim/l2cache.cc
@@ -46,32 +46,35 @@
#include "l2cache_trace.h"
-mem_fetch * partition_mf_allocator::alloc(new_addr_type addr, mem_access_type type, unsigned size, bool wr ) const
+mem_fetch * partition_mf_allocator::alloc(new_addr_type addr, mem_access_type type, unsigned size, bool wr, unsigned long long cycle ) const
{
assert( wr );
- mem_access_t access( type, addr, size, wr );
+ mem_access_t access( type, addr, size, wr, m_memory_config->gpgpu_ctx );
mem_fetch *mf = new mem_fetch( access,
NULL,
WRITE_PACKET_SIZE,
-1,
-1,
-1,
- m_memory_config );
+ m_memory_config,
+ cycle);
return mf;
}
memory_partition_unit::memory_partition_unit( unsigned partition_id,
- const struct memory_config *config,
- class memory_stats_t *stats )
-: m_id(partition_id), m_config(config), m_stats(stats), m_arbitration_metadata(config)
+ const memory_config *config,
+ class memory_stats_t *stats,
+ class gpgpu_sim* gpu)
+: m_id(partition_id), m_config(config), m_stats(stats), m_arbitration_metadata(config), m_gpu(gpu)
{
- m_dram = new dram_t(m_id,m_config,m_stats,this);
+ m_dram = new dram_t(m_id,m_config,m_stats,this,gpu);
m_sub_partition = new memory_sub_partition*[m_config->m_n_sub_partition_per_memory_channel];
for (unsigned p = 0; p < m_config->m_n_sub_partition_per_memory_channel; p++) {
unsigned sub_partition_id = m_id * m_config->m_n_sub_partition_per_memory_channel + p;
- m_sub_partition[p] = new memory_sub_partition(sub_partition_id, m_config, stats);
+ m_sub_partition[p] = new memory_sub_partition(sub_partition_id, m_config, stats, gpu);
}
+
}
void memory_partition_unit::handle_memcpy_to_gpu( size_t addr, unsigned global_subpart_id, mem_access_sector_mask_t mask )
@@ -80,7 +83,7 @@ void memory_partition_unit::handle_memcpy_to_gpu( size_t addr, unsigned global_s
std::string mystring =
mask.to_string<char,std::string::traits_type,std::string::allocator_type>();
MEMPART_DPRINTF("Copy Engine Request Received For Address=%llx, local_subpart=%u, global_subpart=%u, sector_mask=%s \n", addr, p, global_subpart_id, mystring.c_str());
- m_sub_partition[p]->force_l2_tag_update(addr,gpu_sim_cycle+gpu_tot_sim_cycle, mask);
+ m_sub_partition[p]->force_l2_tag_update(addr,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle, mask);
}
memory_partition_unit::~memory_partition_unit()
@@ -92,7 +95,7 @@ memory_partition_unit::~memory_partition_unit()
delete[] m_sub_partition;
}
-memory_partition_unit::arbitration_metadata::arbitration_metadata(const struct memory_config *config)
+memory_partition_unit::arbitration_metadata::arbitration_metadata(const memory_config *config)
: m_last_borrower(config->m_n_sub_partition_per_memory_channel - 1),
m_private_credit(config->m_n_sub_partition_per_memory_channel, 0),
m_shared_credit(0)
@@ -208,7 +211,7 @@ void memory_partition_unit::simple_dram_model_cycle()
// pop completed memory request from dram and push it to dram-to-L2 queue
// of the original sub partition
- if (!m_dram_latency_queue.empty() && ( (gpu_sim_cycle+gpu_tot_sim_cycle) >= m_dram_latency_queue.front().ready_cycle )) {
+ if (!m_dram_latency_queue.empty() && ( (m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle) >= m_dram_latency_queue.front().ready_cycle )) {
mem_fetch* mf_return = m_dram_latency_queue.front().req;
if( mf_return->get_access_type() != L1_WRBK_ACC && mf_return->get_access_type() != L2_WRBK_ACC ) {
mf_return->set_reply();
@@ -222,7 +225,7 @@ void memory_partition_unit::simple_dram_model_cycle()
delete mf_return;
} else {
m_sub_partition[dest_spid]->dram_L2_queue_push(mf_return);
- mf_return->set_status(IN_PARTITION_DRAM_TO_L2_QUEUE,gpu_sim_cycle+gpu_tot_sim_cycle);
+ mf_return->set_status(IN_PARTITION_DRAM_TO_L2_QUEUE,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
m_arbitration_metadata.return_credit(dest_spid);
MEMPART_DPRINTF("mem_fetch request %p return from dram to sub partition %d\n", mf_return, dest_spid);
}
@@ -252,7 +255,7 @@ void memory_partition_unit::simple_dram_model_cycle()
MEMPART_DPRINTF("Issue mem_fetch request %p from sub partition %d to dram\n", mf, spid);
dram_delay_t d;
d.req = mf;
- d.ready_cycle = gpu_sim_cycle+gpu_tot_sim_cycle + m_config->dram_latency;
+ d.ready_cycle = m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle + m_config->dram_latency;
m_dram_latency_queue.push_back(d);
mf->set_status(IN_PARTITION_DRAM_LATENCY_QUEUE,gpu_sim_cycle+gpu_tot_sim_cycle);
m_arbitration_metadata.borrow_credit(spid);
@@ -278,7 +281,7 @@ void memory_partition_unit::dram_cycle()
delete mf_return;
} else {
m_sub_partition[dest_spid]->dram_L2_queue_push(mf_return);
- mf_return->set_status(IN_PARTITION_DRAM_TO_L2_QUEUE,gpu_sim_cycle+gpu_tot_sim_cycle);
+ mf_return->set_status(IN_PARTITION_DRAM_TO_L2_QUEUE,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
m_arbitration_metadata.return_credit(dest_spid);
MEMPART_DPRINTF("mem_fetch request %p return from dram to sub partition %d\n", mf_return, dest_spid);
}
@@ -307,9 +310,9 @@ void memory_partition_unit::dram_cycle()
MEMPART_DPRINTF("Issue mem_fetch request %p from sub partition %d to dram\n", mf, spid);
dram_delay_t d;
d.req = mf;
- d.ready_cycle = gpu_sim_cycle+gpu_tot_sim_cycle + m_config->dram_latency;
+ d.ready_cycle = m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle + m_config->dram_latency;
m_dram_latency_queue.push_back(d);
- mf->set_status(IN_PARTITION_DRAM_LATENCY_QUEUE,gpu_sim_cycle+gpu_tot_sim_cycle);
+ mf->set_status(IN_PARTITION_DRAM_LATENCY_QUEUE,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
m_arbitration_metadata.borrow_credit(spid);
break; // the DRAM should only accept one request per cycle
}
@@ -317,11 +320,11 @@ void memory_partition_unit::dram_cycle()
//}
// DRAM latency queue
- if( !m_dram_latency_queue.empty() && ( (gpu_sim_cycle+gpu_tot_sim_cycle) >= m_dram_latency_queue.front().ready_cycle ) && !m_dram->full(m_dram_latency_queue.front().req->is_write()) ) {
- mem_fetch* mf = m_dram_latency_queue.front().req;
- m_dram_latency_queue.pop_front();
- m_dram->push(mf);
- }
+ if( !m_dram_latency_queue.empty() && ( (m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle) >= m_dram_latency_queue.front().ready_cycle ) && !m_dram->full(m_dram_latency_queue.front().req->is_write()) ) {
+ mem_fetch* mf = m_dram_latency_queue.front().req;
+ m_dram_latency_queue.pop_front();
+ m_dram->push(mf);
+ }
}
void memory_partition_unit::set_done( mem_fetch *mf )
@@ -368,12 +371,14 @@ void memory_partition_unit::print( FILE *fp ) const
}
memory_sub_partition::memory_sub_partition( unsigned sub_partition_id,
- const struct memory_config *config,
- class memory_stats_t *stats )
+ const memory_config *config,
+ class memory_stats_t *stats,
+ class gpgpu_sim* gpu)
{
m_id = sub_partition_id;
m_config=config;
m_stats=stats;
+ m_gpu = gpu;
m_memcpy_cycle_offset = 0;
assert(m_id < m_config->m_n_mem_sub_partition);
@@ -384,7 +389,7 @@ memory_sub_partition::memory_sub_partition( unsigned sub_partition_id,
m_mf_allocator = new partition_mf_allocator(config);
if(!m_config->m_L2_config.disabled())
- m_L2cache = new l2_cache(L2c_name,m_config->m_L2_config,-1,-1,m_L2interface,m_mf_allocator,IN_PARTITION_L2_MISS_QUEUE);
+ m_L2cache = new l2_cache(L2c_name,m_config->m_L2_config,-1,-1,m_L2interface,m_mf_allocator,IN_PARTITION_L2_MISS_QUEUE, gpu);
unsigned int icnt_L2;
unsigned int L2_dram;
@@ -416,7 +421,7 @@ void memory_sub_partition::cache_cycle( unsigned cycle )
mem_fetch *mf = m_L2cache->next_access();
if(mf->get_access_type() != L2_WR_ALLOC_R){ // Don't pass write allocate read request back to upper level cache
mf->set_reply();
- mf->set_status(IN_PARTITION_L2_TO_ICNT_QUEUE,gpu_sim_cycle+gpu_tot_sim_cycle);
+ mf->set_status(IN_PARTITION_L2_TO_ICNT_QUEUE,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
m_L2_icnt_queue->push(mf);
}else{
if(m_config->m_L2_config.m_write_alloc_policy == FETCH_ON_WRITE)
@@ -424,7 +429,7 @@ void memory_sub_partition::cache_cycle( unsigned cycle )
mem_fetch* original_wr_mf = mf->get_original_wr_mf();
assert(original_wr_mf);
original_wr_mf->set_reply();
- original_wr_mf->set_status(IN_PARTITION_L2_TO_ICNT_QUEUE,gpu_sim_cycle+gpu_tot_sim_cycle);
+ original_wr_mf->set_status(IN_PARTITION_L2_TO_ICNT_QUEUE,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
m_L2_icnt_queue->push(original_wr_mf);
}
m_request_tracker.erase(mf);
@@ -438,13 +443,13 @@ void memory_sub_partition::cache_cycle( unsigned cycle )
mem_fetch *mf = m_dram_L2_queue->top();
if ( !m_config->m_L2_config.disabled() && m_L2cache->waiting_for_fill(mf) ) {
if (m_L2cache->fill_port_free()) {
- mf->set_status(IN_PARTITION_L2_FILL_QUEUE,gpu_sim_cycle+gpu_tot_sim_cycle);
- m_L2cache->fill(mf,gpu_sim_cycle+gpu_tot_sim_cycle+m_memcpy_cycle_offset);
+ mf->set_status(IN_PARTITION_L2_FILL_QUEUE,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
+ m_L2cache->fill(mf,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle+m_memcpy_cycle_offset);
m_dram_L2_queue->pop();
}
} else if ( !m_L2_icnt_queue->full() ) {
if(mf->is_write() && mf->get_type() == WRITE_ACK)
- mf->set_status(IN_PARTITION_L2_TO_ICNT_QUEUE,gpu_sim_cycle+gpu_tot_sim_cycle);
+ mf->set_status(IN_PARTITION_L2_TO_ICNT_QUEUE,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
m_L2_icnt_queue->push(mf);
m_dram_L2_queue->pop();
}
@@ -465,7 +470,7 @@ void memory_sub_partition::cache_cycle( unsigned cycle )
bool port_free = m_L2cache->data_port_free();
if ( !output_full && port_free ) {
std::list<cache_event> events;
- enum cache_request_status status = m_L2cache->access(mf->get_addr(),mf,gpu_sim_cycle+gpu_tot_sim_cycle+m_memcpy_cycle_offset,events);
+ enum cache_request_status status = m_L2cache->access(mf->get_addr(),mf,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle+m_memcpy_cycle_offset,events);
bool write_sent = was_write_sent(events);
bool read_sent = was_read_sent(events);
MEM_SUBPART_DPRINTF("Probing L2 cache Address=%llx, status=%u\n", mf->get_addr(), status);
@@ -479,7 +484,7 @@ void memory_sub_partition::cache_cycle( unsigned cycle )
delete mf;
} else {
mf->set_reply();
- mf->set_status(IN_PARTITION_L2_TO_ICNT_QUEUE,gpu_sim_cycle+gpu_tot_sim_cycle);
+ mf->set_status(IN_PARTITION_L2_TO_ICNT_QUEUE,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
m_L2_icnt_queue->push(mf);
}
m_icnt_L2_queue->pop();
@@ -490,7 +495,7 @@ void memory_sub_partition::cache_cycle( unsigned cycle )
} else if ( status != RESERVATION_FAIL ) {
if(mf->is_write() && (m_config->m_L2_config.m_write_alloc_policy == FETCH_ON_WRITE || m_config->m_L2_config.m_write_alloc_policy == LAZY_FETCH_ON_READ) && !was_writeallocate_sent(events)) {
mf->set_reply();
- mf->set_status(IN_PARTITION_L2_TO_ICNT_QUEUE,gpu_sim_cycle+gpu_tot_sim_cycle);
+ mf->set_status(IN_PARTITION_L2_TO_ICNT_QUEUE,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
m_L2_icnt_queue->push(mf);
}
// L2 cache accepted request
@@ -503,7 +508,7 @@ void memory_sub_partition::cache_cycle( unsigned cycle )
}
} else {
// L2 is disabled or non-texture access to texture-only L2
- mf->set_status(IN_PARTITION_L2_TO_DRAM_QUEUE,gpu_sim_cycle+gpu_tot_sim_cycle);
+ mf->set_status(IN_PARTITION_L2_TO_DRAM_QUEUE,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
m_L2_dram_queue->push(mf);
m_icnt_L2_queue->pop();
}
@@ -514,7 +519,7 @@ void memory_sub_partition::cache_cycle( unsigned cycle )
mem_fetch* mf = m_rop.front().req;
m_rop.pop();
m_icnt_L2_queue->push(mf);
- mf->set_status(IN_PARTITION_ICNT_TO_L2_QUEUE,gpu_sim_cycle+gpu_tot_sim_cycle);
+ mf->set_status(IN_PARTITION_ICNT_TO_L2_QUEUE,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
}
}
@@ -694,7 +699,8 @@ std::vector<mem_fetch*> memory_sub_partition::breakdown_request_to_sector_reques
mf->is_write(),
mf->get_access_warp_mask(),
mf->get_access_byte_mask() & byte_sector_mask,
- std::bitset<SECTOR_CHUNCK_SIZE>().set(j));
+ std::bitset<SECTOR_CHUNCK_SIZE>().set(j),
+ m_gpu->gpgpu_ctx);
mem_fetch *n_mf = new mem_fetch( *ma,
NULL,
@@ -703,6 +709,7 @@ std::vector<mem_fetch*> memory_sub_partition::breakdown_request_to_sector_reques
mf->get_sid(),
mf->get_tpc(),
mf->get_mem_config(),
+ m_gpu->gpu_tot_sim_cycle+m_gpu->gpu_sim_cycle,
mf);
result.push_back(n_mf);
@@ -732,13 +739,13 @@ void memory_sub_partition::push( mem_fetch* m_req, unsigned long long cycle )
m_request_tracker.insert(req);
if( req->istexture() ) {
m_icnt_L2_queue->push(req);
- req->set_status(IN_PARTITION_ICNT_TO_L2_QUEUE,gpu_sim_cycle+gpu_tot_sim_cycle);
+ req->set_status(IN_PARTITION_ICNT_TO_L2_QUEUE,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
} else {
rop_delay_t r;
r.req = req;
r.ready_cycle = cycle + m_config->rop_latency;
m_rop.push(r);
- req->set_status(IN_PARTITION_ROP_DELAY,gpu_sim_cycle+gpu_tot_sim_cycle);
+ req->set_status(IN_PARTITION_ROP_DELAY,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
}
}
}
diff --git a/src/gpgpu-sim/l2cache.h b/src/gpgpu-sim/l2cache.h
index 9a51c0e..0f6fe32 100644
--- a/src/gpgpu-sim/l2cache.h
+++ b/src/gpgpu-sim/l2cache.h
@@ -42,12 +42,12 @@ public:
{
m_memory_config = config;
}
- virtual mem_fetch * alloc(const class warp_inst_t &inst, const mem_access_t &access) const
+ virtual mem_fetch * alloc(const class warp_inst_t &inst, const mem_access_t &access, unsigned long long cycle) const
{
abort();
return NULL;
}
- virtual mem_fetch * alloc(new_addr_type addr, mem_access_type type, unsigned size, bool wr) const;
+ virtual mem_fetch * alloc(new_addr_type addr, mem_access_type type, unsigned size, bool wr, unsigned long long cycle) const;
private:
const memory_config *m_memory_config;
};
@@ -58,7 +58,7 @@ private:
class memory_partition_unit
{
public:
- memory_partition_unit( unsigned partition_id, const struct memory_config *config, class memory_stats_t *stats );
+ memory_partition_unit( unsigned partition_id, const memory_config *config, class memory_stats_t *stats, class gpgpu_sim* gpu );
~memory_partition_unit();
bool busy() const;
@@ -94,10 +94,12 @@ public:
unsigned get_mpid() const { return m_id; }
+ class gpgpu_sim* get_mgpu() const { return m_gpu; }
+
private:
unsigned m_id;
- const struct memory_config *m_config;
+ const memory_config *m_config;
class memory_stats_t *m_stats;
class memory_sub_partition **m_sub_partition;
class dram_t *m_dram;
@@ -105,7 +107,7 @@ private:
class arbitration_metadata
{
public:
- arbitration_metadata(const struct memory_config *config);
+ arbitration_metadata(const memory_config *config);
// check if a subpartition still has credit
bool has_credits(int inner_sub_partition_id) const;
@@ -129,7 +131,7 @@ private:
std::vector<int> m_private_credit;
int m_shared_credit;
};
- arbitration_metadata m_arbitration_metadata;
+ arbitration_metadata m_arbitration_metadata;
// determine wheither a given subpartition can issue to DRAM
bool can_issue_to_dram(int inner_sub_partition_id);
@@ -141,12 +143,14 @@ private:
class mem_fetch* req;
};
std::list<dram_delay_t> m_dram_latency_queue;
+
+ class gpgpu_sim* m_gpu;
};
class memory_sub_partition
{
public:
- memory_sub_partition( unsigned sub_partition_id, const struct memory_config *config, class memory_stats_t *stats );
+ memory_sub_partition( unsigned sub_partition_id, const memory_config *config, class memory_stats_t *stats, class gpgpu_sim* gpu );
~memory_sub_partition();
unsigned get_id() const { return m_id; }
@@ -194,9 +198,10 @@ public:
private:
// data
unsigned m_id; //< the global sub partition ID
- const struct memory_config *m_config;
+ const memory_config *m_config;
class l2_cache *m_L2cache;
class L2interface *m_L2interface;
+ class gpgpu_sim* m_gpu;
partition_mf_allocator *m_mf_allocator;
// model delay of ROP units with a fixed latency
diff --git a/src/gpgpu-sim/l2cache_trace.h b/src/gpgpu-sim/l2cache_trace.h
index 2235cdc..d2dd948 100644
--- a/src/gpgpu-sim/l2cache_trace.h
+++ b/src/gpgpu-sim/l2cache_trace.h
@@ -42,7 +42,7 @@
#define MEMPART_DPRINTF(...) do {\
if (MEMPART_DTRACE(MEMORY_PARTITION_UNIT)) {\
printf( MEMPART_PRINT_STR,\
- gpu_sim_cycle + gpu_tot_sim_cycle,\
+ m_gpu->gpu_sim_cycle + m_gpu->gpu_tot_sim_cycle,\
Trace::trace_streams_str[Trace::MEMORY_PARTITION_UNIT],\
get_mpid() );\
printf(__VA_ARGS__);\
@@ -52,7 +52,7 @@
#define MEM_SUBPART_DPRINTF(...) do {\
if (MEM_SUBPART_DTRACE(MEMORY_PARTITION_UNIT)) {\
printf( MEM_SUBPART_PRINT_STR,\
- gpu_sim_cycle + gpu_tot_sim_cycle,\
+ m_gpu->gpu_sim_cycle + m_gpu->gpu_tot_sim_cycle,\
Trace::trace_streams_str[Trace::MEMORY_SUBPARTITION_UNIT],\
m_id );\
printf(__VA_ARGS__);\
diff --git a/src/gpgpu-sim/mem_fetch.cc b/src/gpgpu-sim/mem_fetch.cc
index a260a35..6a00889 100644
--- a/src/gpgpu-sim/mem_fetch.cc
+++ b/src/gpgpu-sim/mem_fetch.cc
@@ -39,9 +39,10 @@ mem_fetch::mem_fetch( const mem_access_t &access,
unsigned wid,
unsigned sid,
unsigned tpc,
- const struct memory_config *config,
+ const memory_config *config,
+ unsigned long long cycle,
mem_fetch *m_original_mf,
- mem_fetch *m_original_wr_mf)
+ mem_fetch *m_original_wr_mf):m_access(access)
{
m_request_uid = sm_next_mf_request_uid++;
@@ -58,10 +59,10 @@ mem_fetch::mem_fetch( const mem_access_t &access,
config->m_address_mapping.addrdec_tlx(access.get_addr(),&m_raw_addr);
m_partition_addr = config->m_address_mapping.partition_address(access.get_addr());
m_type = m_access.is_write()?WRITE_REQUEST:READ_REQUEST;
- m_timestamp = gpu_sim_cycle + gpu_tot_sim_cycle;
+ m_timestamp = cycle;
m_timestamp2 = 0;
m_status = MEM_FETCH_INITIALIZED;
- m_status_change = gpu_sim_cycle + gpu_tot_sim_cycle;
+ m_status_change = cycle;
m_mem_config = config;
icnt_flit_size = config->icnt_flit_size;
original_mf = m_original_mf;
diff --git a/src/gpgpu-sim/mem_fetch.h b/src/gpgpu-sim/mem_fetch.h
index e5efffd..1cab9f2 100644
--- a/src/gpgpu-sim/mem_fetch.h
+++ b/src/gpgpu-sim/mem_fetch.h
@@ -47,6 +47,7 @@ enum mf_type {
#undef MF_TUP
#undef MF_TUP_END
+class memory_config;
class mem_fetch {
public:
mem_fetch( const mem_access_t &access,
@@ -55,7 +56,8 @@ public:
unsigned wid,
unsigned sid,
unsigned tpc,
- const struct memory_config *config,
+ const memory_config *config,
+ unsigned long long cycle,
mem_fetch *original_mf = NULL,
mem_fetch *original_wr_mf = NULL);
~mem_fetch();
@@ -148,7 +150,7 @@ private:
static unsigned sm_next_mf_request_uid;
- const struct memory_config *m_mem_config;
+ const memory_config *m_mem_config;
unsigned icnt_flit_size;
mem_fetch* original_mf; //this pointer is set up when a request is divided into sector requests at L2 cache (if the req size > L2 sector size), so the pointer refers to the original request
diff --git a/src/gpgpu-sim/mem_latency_stat.cc b/src/gpgpu-sim/mem_latency_stat.cc
index 11624f4..a1b43a8 100644
--- a/src/gpgpu-sim/mem_latency_stat.cc
+++ b/src/gpgpu-sim/mem_latency_stat.cc
@@ -41,8 +41,9 @@
#include <string.h>
#include <stdlib.h>
#include <stdio.h>
+#include "../../libcuda/gpgpu_context.h"
-memory_stats_t::memory_stats_t( unsigned n_shader, const struct shader_core_config *shader_config, const struct memory_config *mem_config )
+memory_stats_t::memory_stats_t( unsigned n_shader, const shader_core_config *shader_config, const memory_config *mem_config, const class gpgpu_sim* gpu )
{
assert( mem_config->m_valid );
assert( shader_config->m_valid );
@@ -67,6 +68,7 @@ memory_stats_t::memory_stats_t( unsigned n_shader, const struct shader_core_conf
m_n_shader=n_shader;
m_memory_config=mem_config;
+ m_gpu=gpu;
total_n_access=0;
total_n_reads=0;
total_n_writes=0;
@@ -147,7 +149,7 @@ memory_stats_t::memory_stats_t( unsigned n_shader, const struct shader_core_conf
unsigned memory_stats_t::memlatstat_done(mem_fetch *mf )
{
unsigned mf_latency;
- mf_latency = (gpu_sim_cycle+gpu_tot_sim_cycle) - mf->get_timestamp();
+ mf_latency = (m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle) - mf->get_timestamp();
mf_num_lat_pw++;
mf_tot_lat_pw += mf_latency;
unsigned idx = LOGB2(mf_latency);
@@ -167,7 +169,7 @@ void memory_stats_t::memlatstat_read_done(mem_fetch *mf)
if (mf_latency > mf_max_lat_table[mf->get_tlx_addr().chip][mf->get_tlx_addr().bk])
mf_max_lat_table[mf->get_tlx_addr().chip][mf->get_tlx_addr().bk] = mf_latency;
unsigned icnt2sh_latency;
- icnt2sh_latency = (gpu_tot_sim_cycle+gpu_sim_cycle) - mf->get_return_timestamp();
+ icnt2sh_latency = (m_gpu->gpu_tot_sim_cycle+m_gpu->gpu_sim_cycle) - mf->get_return_timestamp();
tot_icnt2sh_latency += icnt2sh_latency;
icnt2sh_lat_table[LOGB2(icnt2sh_latency)]++;
if (icnt2sh_latency > max_icnt2sh_latency)
@@ -194,14 +196,14 @@ void memory_stats_t::memlatstat_dram_access(mem_fetch *mf)
mem_access_type_stats[mf->get_access_type()][dram_id][bank]++;
}
if (mf->get_pc() != (unsigned)-1)
- ptx_file_line_stats_add_dram_traffic(mf->get_pc(), mf->get_data_size());
+ m_gpu->gpgpu_ctx->stats->ptx_file_line_stats_add_dram_traffic(mf->get_pc(), mf->get_data_size());
}
void memory_stats_t::memlatstat_icnt2mem_pop(mem_fetch *mf)
{
if (m_memory_config->gpgpu_memlatency_stat) {
unsigned icnt2mem_latency;
- icnt2mem_latency = (gpu_tot_sim_cycle+gpu_sim_cycle) - mf->get_timestamp();
+ icnt2mem_latency = (m_gpu->gpu_tot_sim_cycle+m_gpu->gpu_sim_cycle) - mf->get_timestamp();
tot_icnt2mem_latency += icnt2mem_latency;
icnt2mem_lat_table[LOGB2(icnt2mem_latency)]++;
if (icnt2mem_latency > max_icnt2mem_latency)
diff --git a/src/gpgpu-sim/mem_latency_stat.h b/src/gpgpu-sim/mem_latency_stat.h
index 982b9ae..0c84972 100644
--- a/src/gpgpu-sim/mem_latency_stat.h
+++ b/src/gpgpu-sim/mem_latency_stat.h
@@ -32,11 +32,13 @@
#include <zlib.h>
#include <map>
+class memory_config;
class memory_stats_t {
public:
memory_stats_t( unsigned n_shader,
- const struct shader_core_config *shader_config,
- const struct memory_config *mem_config );
+ const class shader_core_config *shader_config,
+ const memory_config *mem_config,
+ const class gpgpu_sim* gpu);
unsigned memlatstat_done( class mem_fetch *mf );
void memlatstat_read_done( class mem_fetch *mf );
@@ -52,8 +54,9 @@ public:
unsigned m_n_shader;
- const struct shader_core_config *m_shader_config;
- const struct memory_config *m_memory_config;
+ const shader_core_config *m_shader_config;
+ const memory_config *m_memory_config;
+ const class gpgpu_sim* m_gpu;
unsigned max_mrq_latency;
unsigned max_dq_latency;
diff --git a/src/gpgpu-sim/power_interface.cc b/src/gpgpu-sim/power_interface.cc
index 3861b6a..0272aa6 100644
--- a/src/gpgpu-sim/power_interface.cc
+++ b/src/gpgpu-sim/power_interface.cc
@@ -38,7 +38,7 @@ void init_mcpat(const gpgpu_sim_config &config, class gpgpu_sim_wrapper *wrapper
}
-void mcpat_cycle(const gpgpu_sim_config &config, const struct shader_core_config *shdr_config, class gpgpu_sim_wrapper *wrapper, class power_stat_t *power_stats, unsigned stat_sample_freq, unsigned tot_cycle, unsigned cycle, unsigned tot_inst, unsigned inst){
+void mcpat_cycle(const gpgpu_sim_config &config, const shader_core_config *shdr_config, class gpgpu_sim_wrapper *wrapper, class power_stat_t *power_stats, unsigned stat_sample_freq, unsigned tot_cycle, unsigned cycle, unsigned tot_inst, unsigned inst){
static bool mcpat_init=true;
diff --git a/src/gpgpu-sim/power_interface.h b/src/gpgpu-sim/power_interface.h
index afac22b..a388c23 100644
--- a/src/gpgpu-sim/power_interface.h
+++ b/src/gpgpu-sim/power_interface.h
@@ -36,7 +36,7 @@
#include "gpgpu_sim_wrapper.h"
void init_mcpat(const gpgpu_sim_config &config, class gpgpu_sim_wrapper *wrapper, unsigned stat_sample_freq, unsigned tot_inst, unsigned inst);
-void mcpat_cycle(const gpgpu_sim_config &config, const struct shader_core_config *shdr_config, class gpgpu_sim_wrapper *wrapper, class power_stat_t *power_stats,
+void mcpat_cycle(const gpgpu_sim_config &config, const shader_core_config *shdr_config, class gpgpu_sim_wrapper *wrapper, class power_stat_t *power_stats,
unsigned stat_sample_freq, unsigned tot_cycle, unsigned cycle, unsigned tot_inst, unsigned inst);
void mcpat_reset_perf_count(class gpgpu_sim_wrapper *wrapper);
diff --git a/src/gpgpu-sim/power_stat.cc b/src/gpgpu-sim/power_stat.cc
index 4c995e9..2c02082 100644
--- a/src/gpgpu-sim/power_stat.cc
+++ b/src/gpgpu-sim/power_stat.cc
@@ -42,7 +42,7 @@
-power_mem_stat_t::power_mem_stat_t(const struct memory_config *mem_config, const struct shader_core_config *shdr_config, memory_stats_t *mem_stats, shader_core_stats *shdr_stats){
+power_mem_stat_t::power_mem_stat_t(const memory_config *mem_config, const shader_core_config *shdr_config, memory_stats_t *mem_stats, shader_core_stats *shdr_stats){
assert( mem_config->m_valid );
m_mem_stats = mem_stats;
m_config = mem_config;
@@ -125,7 +125,7 @@ void power_mem_stat_t::print (FILE *fout) const {
}
-power_core_stat_t::power_core_stat_t( const struct shader_core_config *shader_config, shader_core_stats *core_stats )
+power_core_stat_t::power_core_stat_t( const shader_core_config *shader_config, shader_core_stats *core_stats )
{
assert( shader_config->m_valid );
m_config = shader_config;
@@ -266,7 +266,7 @@ for(unsigned i=0; i<m_config->num_shader(); ++i){
}
}
-power_stat_t::power_stat_t( const struct shader_core_config *shader_config,float * average_pipeline_duty_cycle,float *active_sms,shader_core_stats * shader_stats, const struct memory_config *mem_config,memory_stats_t * memory_stats)
+power_stat_t::power_stat_t( const shader_core_config *shader_config,float * average_pipeline_duty_cycle,float *active_sms,shader_core_stats * shader_stats, const memory_config *mem_config,memory_stats_t * memory_stats)
{
assert( shader_config->m_valid );
assert( mem_config->m_valid );
diff --git a/src/gpgpu-sim/power_stat.h b/src/gpgpu-sim/power_stat.h
index 20af2e5..24ade99 100644
--- a/src/gpgpu-sim/power_stat.h
+++ b/src/gpgpu-sim/power_stat.h
@@ -73,7 +73,7 @@ struct shader_core_power_stats_pod {
class power_core_stat_t : public shader_core_power_stats_pod {
public:
- power_core_stat_t(const struct shader_core_config *shader_config, shader_core_stats *core_stats);
+ power_core_stat_t(const shader_core_config *shader_config, shader_core_stats *core_stats);
void visualizer_print( gzFile visualizer_file );
void print (FILE *fout);
void init();
@@ -113,7 +113,7 @@ struct mem_power_stats_pod{
class power_mem_stat_t : public mem_power_stats_pod{
public:
- power_mem_stat_t(const struct memory_config *mem_config, const struct shader_core_config *shdr_config, memory_stats_t *mem_stats, shader_core_stats *shdr_stats);
+ power_mem_stat_t(const memory_config *mem_config, const shader_core_config *shdr_config, memory_stats_t *mem_stats, shader_core_stats *shdr_stats);
void visualizer_print( gzFile visualizer_file );
void print (FILE *fout) const;
void init();
@@ -128,7 +128,7 @@ private:
class power_stat_t {
public:
- power_stat_t( const struct shader_core_config *shader_config,float * average_pipeline_duty_cycle,float * active_sms,shader_core_stats * shader_stats, const struct memory_config *mem_config,memory_stats_t * memory_stats);
+ power_stat_t( const shader_core_config *shader_config,float * average_pipeline_duty_cycle,float * active_sms,shader_core_stats * shader_stats, const memory_config *mem_config,memory_stats_t * memory_stats);
void visualizer_print( gzFile visualizer_file );
void print (FILE *fout) const;
void save_stats(){
@@ -621,7 +621,7 @@ public:
float * m_average_pipeline_duty_cycle;
float * m_active_sms;
const shader_core_config *m_config;
- const struct memory_config *m_mem_config;
+ const memory_config *m_mem_config;
};
diff --git a/src/gpgpu-sim/scoreboard.cc b/src/gpgpu-sim/scoreboard.cc
index ebec891..80f95c6 100644
--- a/src/gpgpu-sim/scoreboard.cc
+++ b/src/gpgpu-sim/scoreboard.cc
@@ -32,13 +32,15 @@
//Constructor
-Scoreboard::Scoreboard( unsigned sid, unsigned n_warps )
+Scoreboard::Scoreboard( unsigned sid, unsigned n_warps, class gpgpu_t* gpu )
: longopregs()
{
m_sid = sid;
//Initialize size of table
reg_table.resize(n_warps);
longopregs.resize(n_warps);
+
+ m_gpu = gpu;
}
// Print scoreboard contents
diff --git a/src/gpgpu-sim/scoreboard.h b/src/gpgpu-sim/scoreboard.h
index 4a76ea3..a4baa19 100644
--- a/src/gpgpu-sim/scoreboard.h
+++ b/src/gpgpu-sim/scoreboard.h
@@ -38,7 +38,7 @@
class Scoreboard {
public:
- Scoreboard( unsigned sid, unsigned n_warps );
+ Scoreboard( unsigned sid, unsigned n_warps, class gpgpu_t* gpu );
void reserveRegisters(const warp_inst_t *inst);
void releaseRegisters(const warp_inst_t *inst);
@@ -59,6 +59,8 @@ private:
std::vector< std::set<unsigned> > reg_table;
//Register that depend on a long operation (global, local or tex memory)
std::vector< std::set<unsigned> > longopregs;
+
+ class gpgpu_t* m_gpu;
};
diff --git a/src/gpgpu-sim/shader.cc b/src/gpgpu-sim/shader.cc
index e38eefd..c697450 100644
--- a/src/gpgpu-sim/shader.cc
+++ b/src/gpgpu-sim/shader.cc
@@ -28,7 +28,6 @@
#include <float.h>
#include "shader.h"
-#include "gpu-sim.h"
#include "addrdec.h"
#include "dram.h"
#include "stat-tool.h"
@@ -46,12 +45,26 @@
#include <limits.h>
#include "traffic_breakdown.h"
#include "shader_trace.h"
+#include "../../libcuda/gpgpu_context.h"
#define PRIORITIZE_MSHR_OVER_WB 1
#define MAX(a,b) (((a)>(b))?(a):(b))
#define MIN(a,b) (((a)<(b))?(a):(b))
+mem_fetch *shader_core_mem_fetch_allocator::alloc( new_addr_type addr, mem_access_type type, unsigned size, bool wr, unsigned long long cycle ) const
+{
+ mem_access_t access( type, addr, size, wr, m_memory_config->gpgpu_ctx);
+ mem_fetch *mf = new mem_fetch( access,
+ NULL,
+ wr?WRITE_PACKET_SIZE:READ_PACKET_SIZE,
+ -1,
+ m_core_id,
+ m_cluster_id,
+ m_memory_config,
+ cycle);
+ return mf;
+}
/////////////////////////////////////////////////////////////////////////////
std::list<unsigned> shader_core_ctx::get_regs_written( const inst_t &fvt ) const
@@ -69,8 +82,8 @@ shader_core_ctx::shader_core_ctx( class gpgpu_sim *gpu,
class simt_core_cluster *cluster,
unsigned shader_id,
unsigned tpc_id,
- const struct shader_core_config *config,
- const struct memory_config *mem_config,
+ const shader_core_config *config,
+ const memory_config *mem_config,
shader_core_stats *stats )
: core_t( gpu, NULL, config->warp_size, config->n_thread_per_shader ),
m_barriers( this, config->max_warps_per_shader, config->max_cta_per_core, config->max_barriers_per_cta, config->warp_size ),
@@ -133,7 +146,7 @@ shader_core_ctx::shader_core_ctx( class gpgpu_sim *gpu,
m_L1I = new read_only_cache( name,m_config->m_L1I_config,m_sid,get_shader_instruction_cache_id(),m_icnt,IN_L1I_MISS_QUEUE);
m_warp.resize(m_config->max_warps_per_shader, shd_warp_t(this, warp_size));
- m_scoreboard = new Scoreboard(m_sid, m_config->max_warps_per_shader);
+ m_scoreboard = new Scoreboard(m_sid, m_config->max_warps_per_shader, gpu);
//scedulers
//must currently occur after all inputs have been initialized.
@@ -731,7 +744,7 @@ void shader_core_ctx::decode()
if( m_inst_fetch_buffer.m_valid ) {
// decode 1 or 2 instructions and place them into ibuffer
address_type pc = m_inst_fetch_buffer.m_pc;
- const warp_inst_t* pI1 = ptx_fetch_inst(pc);
+ const warp_inst_t* pI1 = m_gpu->gpgpu_ctx->ptx_fetch_inst(pc);
m_warp[m_inst_fetch_buffer.m_warp_id].ibuffer_fill(0,pI1);
m_warp[m_inst_fetch_buffer.m_warp_id].inc_inst_in_pipeline();
if( pI1 ) {
@@ -741,7 +754,7 @@ void shader_core_ctx::decode()
}else if(pI1->oprnd_type==FP_OP) {
m_stats->m_num_FPdecoded_insn[m_sid]++;
}
- const warp_inst_t* pI2 = ptx_fetch_inst(pc+pI1->isize);
+ const warp_inst_t* pI2 = m_gpu->gpgpu_ctx->ptx_fetch_inst(pc+pI1->isize);
if( pI2 ) {
m_warp[m_inst_fetch_buffer.m_warp_id].ibuffer_fill(1,pI2);
m_warp[m_inst_fetch_buffer.m_warp_id].inc_inst_in_pipeline();
@@ -767,7 +780,7 @@ void shader_core_ctx::fetch()
m_inst_fetch_buffer = ifetch_buffer_t(m_warp[mf->get_wid()].get_pc(), mf->get_access_size(), mf->get_wid());
assert( m_warp[mf->get_wid()].get_pc() == (mf->get_addr()-PROGRAM_MEM_START)); // Verify that we got the instruction we were expecting.
m_inst_fetch_buffer.m_valid = true;
- m_warp[mf->get_wid()].set_last_fetch(gpu_sim_cycle);
+ m_warp[mf->get_wid()].set_last_fetch(m_gpu->gpu_sim_cycle);
delete mf;
}
else {
@@ -808,24 +821,26 @@ void shader_core_ctx::fetch()
// TODO: replace with use of allocator
// mem_fetch *mf = m_mem_fetch_allocator->alloc()
- mem_access_t acc(INST_ACC_R,ppc,nbytes,false);
+ mem_access_t acc(INST_ACC_R,ppc,nbytes,false, m_gpu->gpgpu_ctx);
mem_fetch *mf = new mem_fetch(acc,
NULL/*we don't have an instruction yet*/,
READ_PACKET_SIZE,
warp_id,
m_sid,
m_tpc,
- m_memory_config );
+ m_memory_config,
+ m_gpu->gpu_tot_sim_cycle+m_gpu->gpu_sim_cycle
+ );
std::list<cache_event> events;
- enum cache_request_status status = m_L1I->access( (new_addr_type)ppc, mf, gpu_sim_cycle+gpu_tot_sim_cycle,events);
+ enum cache_request_status status = m_L1I->access( (new_addr_type)ppc, mf, m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle,events);
if( status == MISS ) {
m_last_warp_fetched=warp_id;
m_warp[warp_id].set_imiss_pending();
- m_warp[warp_id].set_last_fetch(gpu_sim_cycle);
+ m_warp[warp_id].set_last_fetch(m_gpu->gpu_sim_cycle);
} else if( status == HIT ) {
m_last_warp_fetched=warp_id;
m_inst_fetch_buffer = ifetch_buffer_t(pc,nbytes,warp_id);
- m_warp[warp_id].set_last_fetch(gpu_sim_cycle);
+ m_warp[warp_id].set_last_fetch(m_gpu->gpu_sim_cycle);
delete mf;
} else {
m_last_warp_fetched=warp_id;
@@ -859,7 +874,7 @@ void shader_core_ctx::issue_warp( register_set& pipe_reg_set, const warp_inst_t*
m_warp[warp_id].ibuffer_free();
assert(next_inst->valid());
**pipe_reg = *next_inst; // static instruction information
- (*pipe_reg)->issue( active_mask, warp_id, gpu_tot_sim_cycle + gpu_sim_cycle, m_warp[warp_id].get_dynamic_warp_id(), sch_id ); // dynamic instruction information
+ (*pipe_reg)->issue( active_mask, warp_id, m_gpu->gpu_tot_sim_cycle + m_gpu->gpu_sim_cycle, m_warp[warp_id].get_dynamic_warp_id(), sch_id ); // dynamic instruction information
m_stats->shader_cycle_distro[2+(*pipe_reg)->active_count()]++;
func_exec_inst( **pipe_reg );
if( next_inst->op == BARRIER_OP ){
@@ -1022,7 +1037,7 @@ void scheduler_unit::cycle()
m_simt_stack[warp_id]->get_pdom_stack_top_info(&pc,&rpc);
SCHED_DPRINTF( "Warp (warp_id %u, dynamic_warp_id %u) has valid instruction (%s)\n",
(*iter)->get_warp_id(), (*iter)->get_dynamic_warp_id(),
- ptx_get_insn_str( pc).c_str() );
+ m_shader->m_config->gpgpu_ctx->func_sim->ptx_get_insn_str( pc).c_str() );
if( pI ) {
assert(valid);
if( pc != pI->pc ) {
@@ -1081,12 +1096,11 @@ void scheduler_unit::cycle()
if(pI->m_is_cdp && !warp(warp_id).m_cdp_dummy) {
assert(warp(warp_id).m_cdp_latency == 0);
- extern unsigned cdp_latency[5];
if(pI->m_is_cdp == 1)
- warp(warp_id).m_cdp_latency = cdp_latency[pI->m_is_cdp - 1];
+ warp(warp_id).m_cdp_latency = m_shader->m_config->gpgpu_ctx->func_sim->cdp_latency[pI->m_is_cdp - 1];
else //cudaLaunchDeviceV2 and cudaGetParameterBufferV2
- warp(warp_id).m_cdp_latency = cdp_latency[pI->m_is_cdp - 1]
- + cdp_latency[pI->m_is_cdp] * active_mask.count();
+ warp(warp_id).m_cdp_latency = m_shader->m_config->gpgpu_ctx->func_sim->cdp_latency[pI->m_is_cdp - 1]
+ + m_shader->m_config->gpgpu_ctx->func_sim->cdp_latency[pI->m_is_cdp] * active_mask.count();
warp(warp_id).m_cdp_dummy = true;
break;
}
@@ -1514,7 +1528,7 @@ void shader_core_ctx::warp_inst_complete(const warp_inst_t &inst)
m_stats->m_num_sim_winsn[m_sid]++;
m_gpu->gpu_sim_insn += inst.active_count();
- inst.completed(gpu_tot_sim_cycle + gpu_sim_cycle);
+ inst.completed(m_gpu->gpu_tot_sim_cycle + m_gpu->gpu_sim_cycle);
}
void shader_core_ctx::writeback()
@@ -1552,9 +1566,9 @@ void shader_core_ctx::writeback()
m_warp[warp_id].dec_inst_in_pipeline();
warp_inst_complete(*pipe_reg);
m_gpu->gpu_sim_insn_last_update_sid = m_sid;
- m_gpu->gpu_sim_insn_last_update = gpu_sim_cycle;
- m_last_inst_gpu_sim_cycle = gpu_sim_cycle;
- m_last_inst_gpu_tot_sim_cycle = gpu_tot_sim_cycle;
+ m_gpu->gpu_sim_insn_last_update = m_gpu->gpu_sim_cycle;
+ m_last_inst_gpu_sim_cycle = m_gpu->gpu_sim_cycle;
+ m_last_inst_gpu_tot_sim_cycle = m_gpu->gpu_tot_sim_cycle;
pipe_reg->clear();
preg = m_pipeline_reg[EX_WB].get_ready();
pipe_reg = (preg==NULL)? NULL:*preg;
@@ -1633,9 +1647,9 @@ mem_stage_stall_type ldst_unit::process_memory_access_queue( cache_t *cache, war
return DATA_PORT_STALL;
//const mem_access_t &access = inst.accessq_back();
- mem_fetch *mf = m_mf_allocator->alloc(inst,inst.accessq_back());
+ mem_fetch *mf = m_mf_allocator->alloc(inst,inst.accessq_back(),m_core->get_gpu()->gpu_sim_cycle+m_core->get_gpu()->gpu_tot_sim_cycle);
std::list<cache_event> events;
- enum cache_request_status status = cache->access(mf->get_addr(),mf,gpu_sim_cycle+gpu_tot_sim_cycle,events);
+ enum cache_request_status status = cache->access(mf->get_addr(),mf,m_core->get_gpu()->gpu_sim_cycle+m_core->get_gpu()->gpu_tot_sim_cycle,events);
return process_cache_access( cache, mf->get_addr(), inst, events, mf, status );
}
@@ -1645,7 +1659,7 @@ mem_stage_stall_type ldst_unit::process_memory_access_queue_l1cache( l1_cache *c
if( inst.accessq_empty() )
return result;
- mem_fetch *mf = m_mf_allocator->alloc(inst,inst.accessq_back());
+ mem_fetch *mf = m_mf_allocator->alloc(inst,inst.accessq_back(),m_core->get_gpu()->gpu_sim_cycle+m_core->get_gpu()->gpu_tot_sim_cycle);
if(m_config->m_L1D_config.l1_latency > 0)
{
@@ -1675,7 +1689,7 @@ mem_stage_stall_type ldst_unit::process_memory_access_queue_l1cache( l1_cache *c
else
{
std::list<cache_event> events;
- enum cache_request_status status = cache->access(mf->get_addr(),mf,gpu_sim_cycle+gpu_tot_sim_cycle,events);
+ enum cache_request_status status = cache->access(mf->get_addr(),mf,m_core->get_gpu()->gpu_sim_cycle+m_core->get_gpu()->gpu_tot_sim_cycle,events);
return process_cache_access( cache, mf->get_addr(), inst, events, mf, status );
}
}
@@ -1687,7 +1701,7 @@ void ldst_unit::L1_latency_queue_cycle()
{
mem_fetch* mf_next = l1_latency_queue[0];
std::list<cache_event> events;
- enum cache_request_status status = m_L1D->access(mf_next->get_addr(),mf_next,gpu_sim_cycle+gpu_tot_sim_cycle,events);
+ enum cache_request_status status = m_L1D->access(mf_next->get_addr(),mf_next,m_core->get_gpu()->gpu_sim_cycle+m_core->get_gpu()->gpu_tot_sim_cycle,events);
bool write_sent = was_write_sent(events);
bool read_sent = was_read_sent(events);
@@ -1804,7 +1818,7 @@ bool ldst_unit::memory_cycle( warp_inst_t &inst, mem_stage_stall_type &stall_rea
if( m_icnt->full(size, inst.is_store() || inst.isatomic()) ) {
stall_cond = ICNT_RC_FAIL;
} else {
- mem_fetch *mf = m_mf_allocator->alloc(inst,access);
+ mem_fetch *mf = m_mf_allocator->alloc(inst,access,m_core->get_gpu()->gpu_sim_cycle+m_core->get_gpu()->gpu_tot_sim_cycle);
m_icnt->push(mf);
inst.accessq_pop_back();
//inst.clear_active( access.get_warp_mask() );
@@ -1840,7 +1854,7 @@ bool ldst_unit::response_buffer_full() const
void ldst_unit::fill( mem_fetch *mf )
{
- mf->set_status(IN_SHADER_LDST_RESPONSE_FIFO,gpu_sim_cycle+gpu_tot_sim_cycle);
+ mf->set_status(IN_SHADER_LDST_RESPONSE_FIFO,m_core->get_gpu()->gpu_sim_cycle+m_core->get_gpu()->gpu_tot_sim_cycle);
m_response_fifo.push_back(mf);
}
@@ -2115,7 +2129,8 @@ ldst_unit::ldst_unit( mem_fetch_interface *icnt,
get_shader_normal_cache_id(),
m_icnt,
m_mf_allocator,
- IN_L1D_MISS_QUEUE );
+ IN_L1D_MISS_QUEUE,
+ core->get_gpu());
if(m_config->m_L1D_config.l1_latency > 0)
{
@@ -2202,8 +2217,8 @@ void ldst_unit::writeback()
m_core->warp_inst_complete(m_next_wb);
}
m_next_wb.clear();
- m_last_inst_gpu_sim_cycle = gpu_sim_cycle;
- m_last_inst_gpu_tot_sim_cycle = gpu_tot_sim_cycle;
+ m_last_inst_gpu_sim_cycle = m_core->get_gpu()->gpu_sim_cycle;
+ m_last_inst_gpu_tot_sim_cycle = m_core->get_gpu()->gpu_tot_sim_cycle;
}
}
@@ -2311,13 +2326,13 @@ void ldst_unit::cycle()
mem_fetch *mf = m_response_fifo.front();
if (mf->get_access_type() == TEXTURE_ACC_R) {
if (m_L1T->fill_port_free()) {
- m_L1T->fill(mf,gpu_sim_cycle+gpu_tot_sim_cycle);
+ m_L1T->fill(mf,m_core->get_gpu()->gpu_sim_cycle+m_core->get_gpu()->gpu_tot_sim_cycle);
m_response_fifo.pop_front();
}
} else if (mf->get_access_type() == CONST_ACC_R) {
if (m_L1C->fill_port_free()) {
- mf->set_status(IN_SHADER_FETCHED,gpu_sim_cycle+gpu_tot_sim_cycle);
- m_L1C->fill(mf,gpu_sim_cycle+gpu_tot_sim_cycle);
+ mf->set_status(IN_SHADER_FETCHED,m_core->get_gpu()->gpu_sim_cycle+m_core->get_gpu()->gpu_tot_sim_cycle);
+ m_L1C->fill(mf,m_core->get_gpu()->gpu_sim_cycle+m_core->get_gpu()->gpu_tot_sim_cycle);
m_response_fifo.pop_front();
}
} else {
@@ -2337,13 +2352,13 @@ void ldst_unit::cycle()
}
if( bypassL1D ) {
if ( m_next_global == NULL ) {
- mf->set_status(IN_SHADER_FETCHED,gpu_sim_cycle+gpu_tot_sim_cycle);
+ mf->set_status(IN_SHADER_FETCHED,m_core->get_gpu()->gpu_sim_cycle+m_core->get_gpu()->gpu_tot_sim_cycle);
m_response_fifo.pop_front();
m_next_global = mf;
}
} else {
if (m_L1D->fill_port_free()) {
- m_L1D->fill(mf,gpu_sim_cycle+gpu_tot_sim_cycle);
+ m_L1D->fill(mf,m_core->get_gpu()->gpu_sim_cycle+m_core->get_gpu()->gpu_tot_sim_cycle);
m_response_fifo.pop_front();
}
}
@@ -2432,7 +2447,7 @@ void shader_core_ctx::register_cta_thread_exit( unsigned cta_num, kernel_info_t
shader_CTA_count_unlog(m_sid, 1);
SHADER_DPRINTF(LIVENESS, "GPGPU-Sim uArch: Finished CTA #%d (%lld,%lld), %u CTAs running\n",
- cta_num, gpu_sim_cycle, gpu_tot_sim_cycle, m_n_active_cta);
+ cta_num, m_gpu->gpu_sim_cycle, m_gpu->gpu_tot_sim_cycle, m_n_active_cta);
if( m_n_active_cta == 0 ) {
SHADER_DPRINTF(LIVENESS, "GPGPU-Sim uArch: Empty (last released kernel %u \'%s\').\n",
@@ -2686,7 +2701,7 @@ void warp_inst_t::print( FILE *fout ) const
for (unsigned j=0; j<m_config->warp_size; j++)
fprintf(fout, "%c", (active(j)?'1':'0') );
fprintf(fout, "]: ");
- ptx_print_insn( pc, fout );
+ m_config->gpgpu_ctx->func_sim->ptx_print_insn( pc, fout );
fprintf(fout, "\n");
}
void shader_core_ctx::incexecstat(warp_inst_t *&inst)
@@ -2823,7 +2838,7 @@ void shader_core_ctx::display_pipeline(FILE *fout, int print_mem, int mask ) con
{
fprintf(fout, "=================================================\n");
fprintf(fout, "shader %u at cycle %Lu+%Lu (%u threads running)\n", m_sid,
- gpu_tot_sim_cycle, gpu_sim_cycle, m_not_completed);
+ m_gpu->gpu_tot_sim_cycle, m_gpu->gpu_sim_cycle, m_not_completed);
fprintf(fout, "=================================================\n");
dump_warp_state(fout);
@@ -3015,18 +3030,18 @@ void shader_core_config::set_pipeline_latency() {
* [3] MAD
* [4] DIV
*/
- sscanf(opcode_latency_int, "%u,%u,%u,%u,%u",
+ sscanf(gpgpu_ctx->func_sim->opcode_latency_int, "%u,%u,%u,%u,%u",
&int_latency[0],&int_latency[1],&int_latency[2],
&int_latency[3],&int_latency[4]);
- sscanf(opcode_latency_fp, "%u,%u,%u,%u,%u",
+ sscanf(gpgpu_ctx->func_sim->opcode_latency_fp, "%u,%u,%u,%u,%u",
&fp_latency[0],&fp_latency[1],&fp_latency[2],
&fp_latency[3],&fp_latency[4]);
- sscanf(opcode_latency_dp, "%u,%u,%u,%u,%u",
+ sscanf(gpgpu_ctx->func_sim->opcode_latency_dp, "%u,%u,%u,%u,%u",
&dp_latency[0],&dp_latency[1],&dp_latency[2],
&dp_latency[3],&dp_latency[4]);
- sscanf(opcode_latency_sfu, "%u",
+ sscanf(gpgpu_ctx->func_sim->opcode_latency_sfu, "%u",
&sfu_latency);
- sscanf(opcode_latency_tensor, "%u",
+ sscanf(gpgpu_ctx->func_sim->opcode_latency_tensor, "%u",
&tensor_latency);
//all div operation are executed on sfu
@@ -3045,7 +3060,6 @@ void shader_core_ctx::cycle()
if(!isactive() && get_not_completed() == 0)
return;
- elapsed_cycles_sm_tot++;
m_stats->shader_cycles[m_sid]++;
writeback();
execute();
@@ -3222,7 +3236,7 @@ void barrier_set_t::warp_reaches_barrier(unsigned cta_id,unsigned warp_id,warp_i
cta_to_warp_t::iterator w=m_cta_to_warps.find(cta_id);
if( w == m_cta_to_warps.end() ) { // cta is active
- printf("ERROR ** cta_id %u not found in barrier set on cycle %llu+%llu...\n", cta_id, gpu_tot_sim_cycle, gpu_sim_cycle );
+ printf("ERROR ** cta_id %u not found in barrier set on cycle %llu+%llu...\n", cta_id, m_shader->get_gpu()->gpu_tot_sim_cycle, m_shader->get_gpu()->gpu_sim_cycle );
dump();
abort();
}
@@ -3395,8 +3409,8 @@ bool shader_core_ctx::fetch_unit_response_buffer_full() const
void shader_core_ctx::accept_fetch_response( mem_fetch *mf )
{
- mf->set_status(IN_SHADER_FETCHED,gpu_sim_cycle+gpu_tot_sim_cycle);
- m_L1I->fill(mf,gpu_sim_cycle+gpu_tot_sim_cycle);
+ mf->set_status(IN_SHADER_FETCHED,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
+ m_L1I->fill(mf,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
}
bool shader_core_ctx::ldst_unit_response_buffer_full() const
@@ -3784,8 +3798,8 @@ void opndcoll_rfu_t::collector_unit_t::dispatch()
simt_core_cluster::simt_core_cluster( class gpgpu_sim *gpu,
unsigned cluster_id,
- const struct shader_core_config *config,
- const struct memory_config *mem_config,
+ const shader_core_config *config,
+ const memory_config *mem_config,
shader_core_stats *stats,
class memory_stats_t *mstats )
{
@@ -3958,7 +3972,7 @@ void simt_core_cluster::icnt_inject_request_packet(class mem_fetch *mf)
}
m_stats->m_outgoing_traffic_stats->record_traffic(mf, packet_size);
unsigned destination = mf->get_sub_partition_id();
- mf->set_status(IN_ICNT_TO_MEM,gpu_sim_cycle+gpu_tot_sim_cycle);
+ mf->set_status(IN_ICNT_TO_MEM,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
if (!mf->get_is_write() && !mf->isatomic())
::icnt_push(m_cluster_id, m_config->mem2device(destination), (void*)mf, mf->get_ctrl_size() );
else
@@ -3997,7 +4011,7 @@ void simt_core_cluster::icnt_cycle()
// - For write-ack, the packet only has control metadata
unsigned int packet_size = (mf->get_is_write())? mf->get_ctrl_size() : mf->size();
m_stats->m_incoming_traffic_stats->record_traffic(mf, packet_size);
- mf->set_status(IN_CLUSTER_TO_SHADER_QUEUE,gpu_sim_cycle+gpu_tot_sim_cycle);
+ mf->set_status(IN_CLUSTER_TO_SHADER_QUEUE,m_gpu->gpu_sim_cycle+m_gpu->gpu_tot_sim_cycle);
//m_memory_stats->memlatstat_read_done(mf,m_shader_config->max_warps_per_shader);
m_response_fifo.push_back(mf);
m_stats->n_mem_to_simt[m_cluster_id] += mf->get_num_flits(false);
diff --git a/src/gpgpu-sim/shader.h b/src/gpgpu-sim/shader.h
index a0c2b63..b0d7f7f 100644
--- a/src/gpgpu-sim/shader.h
+++ b/src/gpgpu-sim/shader.h
@@ -69,6 +69,8 @@
#define WRITE_MASK_SIZE 8
+class gpgpu_context;
+
enum exec_unit_type_t
{
NONE = 0,
@@ -116,7 +118,6 @@ public:
m_done_exit=true;
m_last_fetch=0;
m_next=0;
- m_inst_at_barrier=NULL;
//Jin: cdp support
m_cdp_latency = 0;
@@ -173,8 +174,8 @@ public:
address_type get_pc() const { return m_next_pc; }
void set_next_pc( address_type pc ) { m_next_pc = pc; }
- void store_info_of_last_inst_at_barrier(const warp_inst_t *pI){ m_inst_at_barrier = pI;}
- const warp_inst_t * restore_info_of_last_inst_at_barrier(){ return m_inst_at_barrier;}
+ void store_info_of_last_inst_at_barrier(const warp_inst_t *pI){ m_inst_at_barrier = *pI;}
+ warp_inst_t * restore_info_of_last_inst_at_barrier(){ return &m_inst_at_barrier;}
void ibuffer_fill( unsigned slot, const warp_inst_t *pI )
{
@@ -264,7 +265,7 @@ private:
bool m_valid;
};
- const warp_inst_t *m_inst_at_barrier;
+ warp_inst_t m_inst_at_barrier;
ibuffer_entry m_ibuffer[IBUFFER_SIZE];
unsigned m_next;
@@ -295,7 +296,7 @@ typedef std::bitset<WARP_PER_CTA_MAX> warp_set_t;
int register_bank(int regnum, int wid, unsigned num_banks, unsigned bank_warp_shift, bool sub_core_model, unsigned banks_per_sched, unsigned sched_id );
class shader_core_ctx;
-struct shader_core_config;
+class shader_core_config;
class shader_core_stats;
enum scheduler_prioritization_type
@@ -1033,7 +1034,7 @@ struct ifetch_buffer_t {
unsigned m_warp_id;
};
-struct shader_core_config;
+class shader_core_config;
class simd_function_unit {
public:
@@ -1363,10 +1364,12 @@ const char* const pipeline_stage_name_decode[] = {
"N_PIPELINE_STAGES"
};
-struct shader_core_config : public core_config
+class shader_core_config : public core_config
{
- shader_core_config(){
+ public:
+ shader_core_config(gpgpu_context* ctx):core_config(ctx){
pipeline_widths_string = NULL;
+ gpgpu_ctx = ctx;
}
void init()
@@ -1426,6 +1429,8 @@ struct shader_core_config : public core_config
unsigned cid_to_sid( unsigned cid, unsigned cluster_id ) const { return cluster_id*n_simt_cores_per_cluster + cid; }
void set_pipeline_latency();
+ // backward pointer
+ class gpgpu_context* gpgpu_ctx;
// data
char *gpgpu_shader_core_pipeline_opt;
bool gpgpu_perfect_mem;
@@ -1722,6 +1727,7 @@ private:
friend class LooseRoundRobbinScheduler;
};
+class memory_config;
class shader_core_mem_fetch_allocator : public mem_fetch_allocator {
public:
shader_core_mem_fetch_allocator( unsigned core_id, unsigned cluster_id, const memory_config *config )
@@ -1730,20 +1736,8 @@ public:
m_cluster_id = cluster_id;
m_memory_config = config;
}
- mem_fetch *alloc( new_addr_type addr, mem_access_type type, unsigned size, bool wr ) const
- {
- mem_access_t access( type, addr, size, wr );
- mem_fetch *mf = new mem_fetch( access,
- NULL,
- wr?WRITE_PACKET_SIZE:READ_PACKET_SIZE,
- -1,
- m_core_id,
- m_cluster_id,
- m_memory_config );
- return mf;
- }
-
- mem_fetch *alloc( const warp_inst_t &inst, const mem_access_t &access ) const
+ mem_fetch *alloc( new_addr_type addr, mem_access_type type, unsigned size, bool wr, unsigned long long cycle ) const;
+ mem_fetch *alloc( const warp_inst_t &inst, const mem_access_t &access, unsigned long long cycle ) const
{
warp_inst_t inst_copy = inst;
mem_fetch *mf = new mem_fetch(access,
@@ -1752,7 +1746,8 @@ public:
inst.warp_id(),
m_core_id,
m_cluster_id,
- m_memory_config);
+ m_memory_config,
+ cycle);
return mf;
}
@@ -1769,8 +1764,8 @@ public:
class simt_core_cluster *cluster,
unsigned shader_id,
unsigned tpc_id,
- const struct shader_core_config *config,
- const struct memory_config *mem_config,
+ const shader_core_config *config,
+ const memory_config *mem_config,
shader_core_stats *stats );
// used by simt_core_cluster:
@@ -2064,8 +2059,8 @@ class simt_core_cluster {
public:
simt_core_cluster( class gpgpu_sim *gpu,
unsigned cluster_id,
- const struct shader_core_config *config,
- const struct memory_config *mem_config,
+ const shader_core_config *config,
+ const memory_config *mem_config,
shader_core_stats *stats,
memory_stats_t *mstats );
diff --git a/src/gpgpu-sim/shader_trace.h b/src/gpgpu-sim/shader_trace.h
index de3e059..ac4e894 100644
--- a/src/gpgpu-sim/shader_trace.h
+++ b/src/gpgpu-sim/shader_trace.h
@@ -44,7 +44,7 @@
#define SHADER_DPRINTF(x, ...) do {\
if (SHADER_DTRACE(x)) {\
printf( SHADER_PRINT_STR,\
- gpu_sim_cycle + gpu_tot_sim_cycle,\
+ m_gpu->gpu_sim_cycle + m_gpu->gpu_tot_sim_cycle,\
Trace::trace_streams_str[Trace::x],\
get_sid() );\
printf(__VA_ARGS__);\
@@ -56,7 +56,7 @@
#define SCHED_DPRINTF(...) do {\
if (SHADER_DTRACE(WARP_SCHEDULER)) {\
printf( SCHED_PRINT_STR,\
- gpu_sim_cycle + gpu_tot_sim_cycle,\
+ m_shader->get_gpu()->gpu_sim_cycle + m_shader->get_gpu()->gpu_tot_sim_cycle,\
Trace::trace_streams_str[Trace::WARP_SCHEDULER],\
get_sid(),\
m_id );\
diff --git a/src/gpgpu-sim/stat-tool.cc b/src/gpgpu-sim/stat-tool.cc
index 6a4c75b..35a4cc3 100644
--- a/src/gpgpu-sim/stat-tool.cc
+++ b/src/gpgpu-sim/stat-tool.cc
@@ -37,6 +37,7 @@
#include <map>
#include <algorithm>
#include <string>
+#include "../../libcuda/gpgpu_context.h"
////////////////////////////////////////////////////////////////////////////////
@@ -110,12 +111,10 @@ void spill_log_to_file (FILE *fout, int final, unsigned long long current_cycle
////////////////////////////////////////////////////////////////////////////////
-unsigned translate_pc_to_ptxlineno(unsigned pc);
-
static int n_thread_CFloggers = 0;
static thread_CFlocality** thread_CFlogger = NULL;
-void create_thread_CFlogger( int n_loggers, int n_threads, address_type start_pc, unsigned long long logging_interval)
+void create_thread_CFlogger(gpgpu_context* ctx, int n_loggers, int n_threads, address_type start_pc, unsigned long long logging_interval)
{
destroy_thread_CFlogger();
@@ -126,7 +125,7 @@ void create_thread_CFlogger( int n_loggers, int n_threads, address_type start_pc
char buffer[32];
for (int i = 0; i < n_thread_CFloggers; i++) {
snprintf(buffer, 32, "%02d", i);
- thread_CFlogger[i] = new thread_CFlocality( name_tpl + buffer, logging_interval, n_threads, start_pc);
+ thread_CFlogger[i] = new thread_CFlocality( ctx, name_tpl + buffer, logging_interval, n_threads, start_pc);
if (logging_interval != 0) {
add_snap_shot_trigger(thread_CFlogger[i]);
add_spill_log(thread_CFlogger[i]);
@@ -368,10 +367,10 @@ static int s_cache_access_logger_n_types = 0;
static std::vector<linear_histogram_logger> s_cache_access_logger;
enum cache_access_logger_types {
- NORMAL, TEXTURE, CONSTANT, INSTRUCTION
+ NORMALS, TEXTURE, CONSTANT, INSTRUCTION
};
-int get_shader_normal_cache_id() { return NORMAL; }
+int get_shader_normal_cache_id() { return NORMALS; }
int get_shader_texture_cache_id() { return TEXTURE; }
int get_shader_constant_cache_id() { return CONSTANT; }
int get_shader_instruction_cache_id() { return INSTRUCTION; }
@@ -394,7 +393,7 @@ void shader_cache_access_log( int logger_id, int type, int miss)
{
if (s_cache_access_logger_n_types == 0) return;
if (logger_id < 0) return;
- assert(type == NORMAL || type == TEXTURE || type == CONSTANT || type == INSTRUCTION);
+ assert(type == NORMALS || type == TEXTURE || type == CONSTANT || type == INSTRUCTION);
assert(miss == 0 || miss == 1);
s_cache_access_logger[logger_id].log(2 * type + miss);
@@ -404,7 +403,7 @@ void shader_cache_access_unlog( int logger_id, int type, int miss)
{
if (s_cache_access_logger_n_types == 0) return;
if (logger_id < 0) return;
- assert(type == NORMAL || type == TEXTURE || type == CONSTANT || type == INSTRUCTION);
+ assert(type == NORMALS || type == TEXTURE || type == CONSTANT || type == INSTRUCTION);
assert(miss == 0 || miss == 1);
s_cache_access_logger[logger_id].unlog(2 * type + miss);
@@ -477,22 +476,24 @@ void shader_CTA_count_visualizer_gzprint( gzFile fout )
////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////
-thread_insn_span::thread_insn_span(unsigned long long cycle)
+thread_insn_span::thread_insn_span(unsigned long long cycle, gpgpu_context* ctx)
: m_cycle(cycle),
#if (tr1_hash_map_ismap == 1)
m_insn_span_count()
#else
m_insn_span_count(32*1024)
#endif
-{
+{
+ gpgpu_ctx = ctx;
}
thread_insn_span::~thread_insn_span() { }
-thread_insn_span::thread_insn_span(const thread_insn_span& other)
+thread_insn_span::thread_insn_span(const thread_insn_span& other, gpgpu_context* ctx)
: m_cycle(other.m_cycle),
- m_insn_span_count(other.m_insn_span_count)
+ m_insn_span_count(other.m_insn_span_count)
{
+ gpgpu_ctx = ctx;
}
thread_insn_span& thread_insn_span::operator=(const thread_insn_span& other)
@@ -551,7 +552,7 @@ void thread_insn_span::print_sparse_histo(FILE *fout) const
int n_printed_entries = 0;
span_count_map::const_iterator i_sc = m_insn_span_count.begin();
for (; i_sc != m_insn_span_count.end(); ++i_sc) {
- unsigned ptx_lineno = translate_pc_to_ptxlineno(i_sc->first);
+ unsigned ptx_lineno = gpgpu_ctx->translate_pc_to_ptxlineno(i_sc->first);
fprintf(fout, "%u %d ", ptx_lineno, i_sc->second);
n_printed_entries++;
}
@@ -566,7 +567,7 @@ void thread_insn_span::print_sparse_histo(gzFile fout) const
int n_printed_entries = 0;
span_count_map::const_iterator i_sc = m_insn_span_count.begin();
for (; i_sc != m_insn_span_count.end(); ++i_sc) {
- unsigned ptx_lineno = translate_pc_to_ptxlineno(i_sc->first);
+ unsigned ptx_lineno = gpgpu_ctx->translate_pc_to_ptxlineno(i_sc->first);
gzprintf(fout, "%u %d ", ptx_lineno, i_sc->second);
n_printed_entries++;
}
@@ -578,14 +579,14 @@ void thread_insn_span::print_sparse_histo(gzFile fout) const
////////////////////////////////////////////////////////////////////////////////
-thread_CFlocality::thread_CFlocality(std::string name,
+thread_CFlocality::thread_CFlocality( gpgpu_context* ctx, std::string name,
unsigned long long snap_shot_interval,
int nthreads,
address_type start_pc,
unsigned long long start_cycle)
: snap_shot_trigger(snap_shot_interval), m_name(name),
m_nthreads(nthreads), m_thread_pc(nthreads, start_pc), m_cycle(start_cycle),
- m_thd_span(start_cycle)
+ m_thd_span(start_cycle, ctx)
{
std::fill(m_thread_pc.begin(), m_thread_pc.end(), -1); // so that hw thread with no work assigned will not clobber results
}
diff --git a/src/gpgpu-sim/stat-tool.h b/src/gpgpu-sim/stat-tool.h
index 5646f01..67b3923 100644
--- a/src/gpgpu-sim/stat-tool.h
+++ b/src/gpgpu-sim/stat-tool.h
@@ -35,6 +35,7 @@
#include <stdio.h>
#include <zlib.h>
+class gpgpu_context;
/////////////////////////////////////////////////////////////////////////////////////
// logger snapshot trigger:
// - automate the snap_shot part of loggers to avoid modifying simulation loop everytime
@@ -80,8 +81,8 @@ public:
class thread_insn_span {
public:
- thread_insn_span(unsigned long long cycle);
- thread_insn_span(const thread_insn_span& other);
+ thread_insn_span(unsigned long long cycle, gpgpu_context* ctx);
+ thread_insn_span(const thread_insn_span& other, gpgpu_context* ctx);
~thread_insn_span();
thread_insn_span& operator=(const thread_insn_span& other);
@@ -94,7 +95,8 @@ public:
void print_sparse_histo(FILE *fout) const;
void print_sparse_histo(gzFile fout) const;
-private:
+private:
+ gpgpu_context* gpgpu_ctx;
typedef tr1_hash_map<address_type, int> span_count_map;
unsigned long long m_cycle;
span_count_map m_insn_span_count;
@@ -102,7 +104,7 @@ private:
class thread_CFlocality : public snap_shot_trigger, public spill_log_interface {
public:
- thread_CFlocality(std::string name, unsigned long long snap_shot_interval,
+ thread_CFlocality(gpgpu_context* ctx, std::string name, unsigned long long snap_shot_interval,
int nthreads, address_type start_pc, unsigned long long start_cycle = 0);
~thread_CFlocality();
@@ -270,7 +272,7 @@ void try_snap_shot (unsigned long long current_cycle);
void set_spill_interval (unsigned long long interval);
void spill_log_to_file (FILE *fout, int final, unsigned long long current_cycle);
-void create_thread_CFlogger( int n_loggers, int n_threads, address_type start_pc, unsigned long long logging_interval);
+void create_thread_CFlogger(gpgpu_context* ctx, int n_loggers, int n_threads, address_type start_pc, unsigned long long logging_interval);
void destroy_thread_CFlogger( );
void cflog_update_thread_pc( int logger_id, int thread_id, address_type pc );
void cflog_snapshot( int logger_id, unsigned long long cycle );
diff --git a/src/gpgpusim_entrypoint.cc b/src/gpgpusim_entrypoint.cc
index 9e2bfa2..816159f 100644
--- a/src/gpgpusim_entrypoint.cc
+++ b/src/gpgpusim_entrypoint.cc
@@ -35,32 +35,30 @@
#include "gpgpu-sim/gpu-sim.h"
#include "gpgpu-sim/icnt_wrapper.h"
#include "stream_manager.h"
-
-#include <pthread.h>
-#include <semaphore.h>
+#include "../libcuda/gpgpu_context.h"
#define MAX(a,b) (((a)>(b))?(a):(b))
+static int sg_argc = 3;
+static const char *sg_argv[] = {"", "-config","gpgpusim.config"};
-struct gpgpu_ptx_sim_arg *grid_params;
-
-sem_t g_sim_signal_start;
-sem_t g_sim_signal_finish;
-sem_t g_sim_signal_exit;
-time_t g_simulation_starttime;
-pthread_t g_simulation_thread;
-
-gpgpu_sim_config g_the_gpu_config;
-gpgpu_sim *g_the_gpu;
-stream_manager *g_stream_manager;
-
+GPGPUsim_ctx* the_gpgpusim = NULL;
+GPGPUsim_ctx* GPGPUsim_ctx_ptr(){
+ if(the_gpgpusim == NULL)
+ the_gpgpusim = GPGPU_Context()->the_gpgpusim;
-static int sg_argc = 3;
-static const char *sg_argv[] = {"", "-config","gpgpusim.config"};
+ return the_gpgpusim;
+}
+class gpgpu_sim* g_the_gpu() {
+ return GPGPUsim_ctx_ptr()->g_the_gpu;
+}
+class stream_manager* g_stream_manager() {
+ return GPGPUsim_ctx_ptr()->g_stream_manager;
+}
static void print_simulation_time();
@@ -69,29 +67,26 @@ void *gpgpu_sim_thread_sequential(void*)
// at most one kernel running at a time
bool done;
do {
- sem_wait(&g_sim_signal_start);
+ sem_wait(&(GPGPUsim_ctx_ptr()->g_sim_signal_start));
done = true;
- if( g_the_gpu->get_more_cta_left() ) {
+ if( GPGPUsim_ctx_ptr()->g_the_gpu->get_more_cta_left() ) {
done = false;
- g_the_gpu->init();
- while( g_the_gpu->active() ) {
- g_the_gpu->cycle();
- g_the_gpu->deadlock_check();
+ GPGPUsim_ctx_ptr()->g_the_gpu->init();
+ while( GPGPUsim_ctx_ptr()->g_the_gpu->active() ) {
+ GPGPUsim_ctx_ptr()->g_the_gpu->cycle();
+ GPGPUsim_ctx_ptr()->g_the_gpu->deadlock_check();
}
- g_the_gpu->print_stats();
- g_the_gpu->update_stats();
+ GPGPUsim_ctx_ptr()->g_the_gpu->print_stats();
+ GPGPUsim_ctx_ptr()->g_the_gpu->update_stats();
print_simulation_time();
}
- sem_post(&g_sim_signal_finish);
+ sem_post(&(GPGPUsim_ctx_ptr()->g_sim_signal_finish));
} while(!done);
- sem_post(&g_sim_signal_exit);
+ sem_post(&(GPGPUsim_ctx_ptr()->g_sim_signal_exit));
return NULL;
}
-pthread_mutex_t g_sim_lock = PTHREAD_MUTEX_INITIALIZER;
-bool g_sim_active = false;
-bool g_sim_done = true;
-bool break_limit = false;
+
static void termination_callback()
{
@@ -108,19 +103,19 @@ void *gpgpu_sim_thread_concurrent(void*)
printf("GPGPU-Sim: *** simulation thread starting and spinning waiting for work ***\n");
fflush(stdout);
}
- while( g_stream_manager->empty_protected() && !g_sim_done )
+ while( GPGPUsim_ctx_ptr()->g_stream_manager->empty_protected() && !GPGPUsim_ctx_ptr()->g_sim_done )
;
if(g_debug_execution >= 3) {
printf("GPGPU-Sim: ** START simulation thread (detected work) **\n");
- g_stream_manager->print(stdout);
+ GPGPUsim_ctx_ptr()->g_stream_manager->print(stdout);
fflush(stdout);
}
- pthread_mutex_lock(&g_sim_lock);
- g_sim_active = true;
- pthread_mutex_unlock(&g_sim_lock);
+ pthread_mutex_lock(&(GPGPUsim_ctx_ptr()->g_sim_lock));
+ GPGPUsim_ctx_ptr()->g_sim_active = true;
+ pthread_mutex_unlock(&(GPGPUsim_ctx_ptr()->g_sim_lock));
bool active = false;
bool sim_cycles = false;
- g_the_gpu->init();
+ GPGPUsim_ctx_ptr()->g_the_gpu->init();
do {
// check if a kernel has completed
// launch operation on device if one is pending and can be run
@@ -132,70 +127,70 @@ void *gpgpu_sim_thread_concurrent(void*)
// another kernel, the gpu is not re-initialized and the inter-kernel
// behaviour may be incorrect. Check that a kernel has finished and
// no other kernel is currently running.
- if(g_stream_manager->operation(&sim_cycles) && !g_the_gpu->active())
+ if(GPGPUsim_ctx_ptr()->g_stream_manager->operation(&sim_cycles) && !GPGPUsim_ctx_ptr()->g_the_gpu->active())
break;
//functional simulation
- if( g_the_gpu->is_functional_sim()) {
- kernel_info_t * kernel = g_the_gpu->get_functional_kernel();
+ if( GPGPUsim_ctx_ptr()->g_the_gpu->is_functional_sim()) {
+ kernel_info_t * kernel = GPGPUsim_ctx_ptr()->g_the_gpu->get_functional_kernel();
assert(kernel);
- gpgpu_cuda_ptx_sim_main_func(*kernel);
- g_the_gpu->finish_functional_sim(kernel);
+ GPGPUsim_ctx_ptr()->gpgpu_ctx->func_sim->gpgpu_cuda_ptx_sim_main_func(*kernel);
+ GPGPUsim_ctx_ptr()->g_the_gpu->finish_functional_sim(kernel);
}
//performance simulation
- if( g_the_gpu->active() ) {
- g_the_gpu->cycle();
- sim_cycles = true;
- g_the_gpu->deadlock_check();
+ if( GPGPUsim_ctx_ptr()->g_the_gpu->active() ) {
+ GPGPUsim_ctx_ptr()->g_the_gpu->cycle();
+ sim_cycles = true;
+ GPGPUsim_ctx_ptr()->g_the_gpu->deadlock_check();
}else {
- if(g_the_gpu->cycle_insn_cta_max_hit()){
- g_stream_manager->stop_all_running_kernels();
- g_sim_done = true;
- break_limit = true;
+ if(GPGPUsim_ctx_ptr()->g_the_gpu->cycle_insn_cta_max_hit()){
+ GPGPUsim_ctx_ptr()->g_stream_manager->stop_all_running_kernels();
+ GPGPUsim_ctx_ptr()->g_sim_done = true;
+ GPGPUsim_ctx_ptr()->break_limit = true;
}
}
- active=g_the_gpu->active() || !g_stream_manager->empty_protected();
+ active=GPGPUsim_ctx_ptr()->g_the_gpu->active() || !(GPGPUsim_ctx_ptr()->g_stream_manager->empty_protected());
- } while( active && !g_sim_done);
+ } while( active && !GPGPUsim_ctx_ptr()->g_sim_done);
if(g_debug_execution >= 3) {
printf("GPGPU-Sim: ** STOP simulation thread (no work) **\n");
fflush(stdout);
}
if(sim_cycles) {
- g_the_gpu->print_stats();
- g_the_gpu->update_stats();
+ GPGPUsim_ctx_ptr()->g_the_gpu->print_stats();
+ GPGPUsim_ctx_ptr()->g_the_gpu->update_stats();
print_simulation_time();
}
- pthread_mutex_lock(&g_sim_lock);
- g_sim_active = false;
- pthread_mutex_unlock(&g_sim_lock);
- } while( !g_sim_done );
+ pthread_mutex_lock(&(GPGPUsim_ctx_ptr()->g_sim_lock));
+ GPGPUsim_ctx_ptr()->g_sim_active = false;
+ pthread_mutex_unlock(&(GPGPUsim_ctx_ptr()->g_sim_lock));
+ } while( !GPGPUsim_ctx_ptr()->g_sim_done );
printf("GPGPU-Sim: *** simulation thread exiting ***\n");
fflush(stdout);
- if(break_limit) {
+ if(GPGPUsim_ctx_ptr()->break_limit) {
printf("GPGPU-Sim: ** break due to reaching the maximum cycles (or instructions) **\n");
exit(1);
}
- sem_post(&g_sim_signal_exit);
+ sem_post(&(GPGPUsim_ctx_ptr()->g_sim_signal_exit));
return NULL;
}
void synchronize()
{
printf("GPGPU-Sim: synchronize waiting for inactive GPU simulation\n");
- g_stream_manager->print(stdout);
+ GPGPUsim_ctx_ptr()->g_stream_manager->print(stdout);
fflush(stdout);
// sem_wait(&g_sim_signal_finish);
bool done = false;
do {
- pthread_mutex_lock(&g_sim_lock);
- done = ( g_stream_manager->empty() && !g_sim_active ) || g_sim_done;
- pthread_mutex_unlock(&g_sim_lock);
+ pthread_mutex_lock(&(GPGPUsim_ctx_ptr()->g_sim_lock));
+ done = ( GPGPUsim_ctx_ptr()->g_stream_manager->empty() && !GPGPUsim_ctx_ptr()->g_sim_active ) || GPGPUsim_ctx_ptr()->g_sim_done;
+ pthread_mutex_unlock(&(GPGPUsim_ctx_ptr()->g_sim_lock));
} while (!done);
printf("GPGPU-Sim: detected inactive GPU simulation thread\n");
fflush(stdout);
@@ -204,29 +199,28 @@ void synchronize()
void exit_simulation()
{
- g_sim_done=true;
+ GPGPUsim_ctx_ptr()->g_sim_done=true;
printf("GPGPU-Sim: exit_simulation called\n");
fflush(stdout);
- sem_wait(&g_sim_signal_exit);
+ sem_wait(&(GPGPUsim_ctx_ptr()->g_sim_signal_exit));
printf("GPGPU-Sim: simulation thread signaled exit\n");
fflush(stdout);
}
-extern bool g_cuda_launch_blocking;
-
-gpgpu_sim *gpgpu_ptx_sim_init_perf()
+gpgpu_sim *gpgpu_context::gpgpu_ptx_sim_init_perf()
{
srand(1);
print_splash();
- read_sim_environment_variables();
- read_parser_environment_variables();
+ func_sim->read_sim_environment_variables();
+ ptx_parser->read_parser_environment_variables();
option_parser_t opp = option_parser_create();
ptx_reg_options(opp);
- ptx_opcocde_latency_options(opp);
+ func_sim->ptx_opcocde_latency_options(opp);
icnt_reg_options(opp);
- g_the_gpu_config.reg_options(opp); // register GPU microrachitecture options
+ GPGPUsim_ctx_ptr()->g_the_gpu_config = new gpgpu_sim_config(this);
+ GPGPUsim_ctx_ptr()->g_the_gpu_config->reg_options(opp); // register GPU microrachitecture options
option_parser_cmdline(opp, sg_argc, sg_argv); // parse configuration options
fprintf(stdout, "GPGPU-Sim: Configuration options:\n\n");
@@ -234,28 +228,28 @@ gpgpu_sim *gpgpu_ptx_sim_init_perf()
// Set the Numeric locale to a standard locale where a decimal point is a "dot" not a "comma"
// so it does the parsing correctly independent of the system environment variables
assert(setlocale(LC_NUMERIC,"C"));
- g_the_gpu_config.init();
+ GPGPUsim_ctx_ptr()->g_the_gpu_config->init();
- g_the_gpu = new gpgpu_sim(g_the_gpu_config);
- g_stream_manager = new stream_manager(g_the_gpu,g_cuda_launch_blocking);
+ GPGPUsim_ctx_ptr()->g_the_gpu = new gpgpu_sim(*(GPGPUsim_ctx_ptr()->g_the_gpu_config), this);
+ GPGPUsim_ctx_ptr()->g_stream_manager = new stream_manager((GPGPUsim_ctx_ptr()->g_the_gpu), func_sim->g_cuda_launch_blocking);
- g_simulation_starttime = time((time_t *)NULL);
+ GPGPUsim_ctx_ptr()->g_simulation_starttime = time((time_t *)NULL);
- sem_init(&g_sim_signal_start,0,0);
- sem_init(&g_sim_signal_finish,0,0);
- sem_init(&g_sim_signal_exit,0,0);
+ sem_init(&(GPGPUsim_ctx_ptr()->g_sim_signal_start),0,0);
+ sem_init(&(GPGPUsim_ctx_ptr()->g_sim_signal_finish),0,0);
+ sem_init(&(GPGPUsim_ctx_ptr()->g_sim_signal_exit),0,0);
- return g_the_gpu;
+ return GPGPUsim_ctx_ptr()->g_the_gpu;
}
void start_sim_thread(int api)
{
- if( g_sim_done ) {
- g_sim_done = false;
+ if( GPGPUsim_ctx_ptr()->g_sim_done ) {
+ GPGPUsim_ctx_ptr()->g_sim_done = false;
if( api == 1 ) {
- pthread_create(&g_simulation_thread,NULL,gpgpu_sim_thread_concurrent,NULL);
+ pthread_create(&(GPGPUsim_ctx_ptr()->g_simulation_thread),NULL,gpgpu_sim_thread_concurrent,NULL);
} else {
- pthread_create(&g_simulation_thread,NULL,gpgpu_sim_thread_sequential,NULL);
+ pthread_create(&(GPGPUsim_ctx_ptr()->g_simulation_thread),NULL,gpgpu_sim_thread_sequential,NULL);
}
}
}
@@ -264,7 +258,7 @@ void print_simulation_time()
{
time_t current_time, difference, d, h, m, s;
current_time = time((time_t *)NULL);
- difference = MAX(current_time - g_simulation_starttime, 1);
+ difference = MAX(current_time - GPGPUsim_ctx_ptr()->g_simulation_starttime, 1);
d = difference/(3600*24);
h = difference/3600 - 24*d;
@@ -274,16 +268,16 @@ void print_simulation_time()
fflush(stderr);
printf("\n\ngpgpu_simulation_time = %u days, %u hrs, %u min, %u sec (%u sec)\n",
(unsigned)d, (unsigned)h, (unsigned)m, (unsigned)s, (unsigned)difference );
- printf("gpgpu_simulation_rate = %u (inst/sec)\n", (unsigned)(g_the_gpu->gpu_tot_sim_insn / difference) );
- printf("gpgpu_simulation_rate = %u (cycle/sec)\n", (unsigned)(gpu_tot_sim_cycle / difference) );
+ printf("gpgpu_simulation_rate = %u (inst/sec)\n", (unsigned)(GPGPUsim_ctx_ptr()->g_the_gpu->gpu_tot_sim_insn / difference) );
+ printf("gpgpu_simulation_rate = %u (cycle/sec)\n", (unsigned)(GPGPUsim_ctx_ptr()->g_the_gpu->gpu_tot_sim_cycle / difference) );
fflush(stdout);
}
int gpgpu_opencl_ptx_sim_main_perf( kernel_info_t *grid )
{
- g_the_gpu->launch(grid);
- sem_post(&g_sim_signal_start);
- sem_wait(&g_sim_signal_finish);
+ GPGPUsim_ctx_ptr()->g_the_gpu->launch(grid);
+ sem_post(&(GPGPUsim_ctx_ptr()->g_sim_signal_start));
+ sem_wait(&(GPGPUsim_ctx_ptr()->g_sim_signal_finish));
return 0;
}
@@ -291,7 +285,7 @@ int gpgpu_opencl_ptx_sim_main_perf( kernel_info_t *grid )
/*!
* This function call the CUDA PTX functional simulator
*/
-int gpgpu_opencl_ptx_sim_main_func( kernel_info_t *grid )
+int cuda_sim::gpgpu_opencl_ptx_sim_main_func( kernel_info_t *grid )
{
//calling the CUDA PTX simulator, sending the kernel by reference and a flag set to true,
//the flag used by the function to distinguish OpenCL calls from the CUDA simulation calls which
diff --git a/src/gpgpusim_entrypoint.h b/src/gpgpusim_entrypoint.h
index bf03f03..887b3c8 100644
--- a/src/gpgpusim_entrypoint.h
+++ b/src/gpgpusim_entrypoint.h
@@ -29,16 +29,59 @@
#define GPGPUSIM_ENTRYPOINT_H_INCLUDED
#include "abstract_hardware_model.h"
-
+#include <pthread.h>
+#include <semaphore.h>
#include <time.h>
-extern time_t g_simulation_starttime;
+//extern time_t g_simulation_starttime;
+class gpgpu_context;
+
+class GPGPUsim_ctx {
+ public:
+ GPGPUsim_ctx(gpgpu_context* ctx) {
+ g_sim_active = false;
+ g_sim_done = true;
+ break_limit = false;
+ g_sim_lock = PTHREAD_MUTEX_INITIALIZER;
+
+ g_the_gpu_config=NULL;
+ g_the_gpu=NULL;
+ g_stream_manager=NULL;
+ the_cude_device=NULL;
+ the_context=NULL;
+ gpgpu_ctx = ctx;
+ }
+
+ //struct gpgpu_ptx_sim_arg *grid_params;
+
+ sem_t g_sim_signal_start;
+ sem_t g_sim_signal_finish;
+ sem_t g_sim_signal_exit;
+ time_t g_simulation_starttime;
+ pthread_t g_simulation_thread;
+ class gpgpu_sim_config *g_the_gpu_config;
+ class gpgpu_sim *g_the_gpu;
+ class stream_manager *g_stream_manager;
+
+ struct _cuda_device_id *the_cude_device;
+ struct CUctx_st* the_context;
+ gpgpu_context* gpgpu_ctx;
+
+
+ pthread_mutex_t g_sim_lock;
+ bool g_sim_active;
+ bool g_sim_done;
+ bool break_limit;
+
+};
-class gpgpu_sim *gpgpu_ptx_sim_init_perf();
void start_sim_thread(int api);
+class gpgpu_sim* g_the_gpu();
+struct GPGPUsim_ctx* GPGPUsim_ctx_ptr();
+class stream_manager* g_stream_manager();
+
int gpgpu_opencl_ptx_sim_main_perf( kernel_info_t *grid );
-int gpgpu_opencl_ptx_sim_main_func( kernel_info_t *grid );
#endif
diff --git a/src/intersim2/Makefile b/src/intersim2/Makefile
index 7d10b3f..3eeeb70 100644
--- a/src/intersim2/Makefile
+++ b/src/intersim2/Makefile
@@ -48,6 +48,7 @@ CPPFLAGS += -O3
endif
CPPFLAGS += -g
CPPFLAGS += -fPIC
+CPPFLAGS += -I$(CUDA_INSTALL_PATH)/include
LFLAGS +=
diff --git a/src/option_parser.cc b/src/option_parser.cc
index 497316f..7d747f0 100644
--- a/src/option_parser.cc
+++ b/src/option_parser.cc
@@ -100,8 +100,7 @@ public:
}
try {
ss >> m_variable;
- } catch (stringstream::failure &e) {
- } catch (exception &e) {
+ } catch (exception &e) {
return false;
}
m_isParsed = true;
diff --git a/src/stream_manager.cc b/src/stream_manager.cc
index 6cd62a2..be3dd71 100644
--- a/src/stream_manager.cc
+++ b/src/stream_manager.cc
@@ -29,6 +29,7 @@
#include "gpgpusim_entrypoint.h"
#include "cuda-sim/cuda-sim.h"
#include "gpgpu-sim/gpu-sim.h"
+#include "../libcuda/gpgpu_context.h"
unsigned CUstream_st::sm_next_stream_uid = 0;
@@ -150,13 +151,13 @@ bool stream_operation::do_operation( gpgpu_sim *gpu )
case stream_memcpy_to_symbol:
if(g_debug_execution >= 3)
printf("memcpy to symbol\n");
- gpgpu_ptx_sim_memcpy_symbol(m_symbol,m_host_address_src,m_cnt,m_offset,1,gpu);
+ gpu->gpgpu_ctx->func_sim->gpgpu_ptx_sim_memcpy_symbol(m_symbol,m_host_address_src,m_cnt,m_offset,1,gpu);
m_stream->record_next_done();
break;
case stream_memcpy_from_symbol:
if(g_debug_execution >= 3)
printf("memcpy from symbol\n");
- gpgpu_ptx_sim_memcpy_symbol(m_symbol,m_host_address_dst,m_cnt,m_offset,0,gpu);
+ gpu->gpgpu_ctx->func_sim->gpgpu_ptx_sim_memcpy_symbol(m_symbol,m_host_address_dst,m_cnt,m_offset,0,gpu);
m_stream->record_next_done();
break;
case stream_kernel_launch:
@@ -190,7 +191,7 @@ bool stream_operation::do_operation( gpgpu_sim *gpu )
case stream_event: {
printf("event update\n");
time_t wallclock = time((time_t *)NULL);
- m_event->update( gpu_tot_sim_cycle, wallclock );
+ m_event->update( gpu->gpu_tot_sim_cycle, wallclock );
m_stream->record_next_done();
}
break;
diff --git a/src/trace.h b/src/trace.h
index a79b4a0..0b96dcf 100644
--- a/src/trace.h
+++ b/src/trace.h
@@ -31,9 +31,6 @@
#ifndef __TRACE_H__
#define __TRACE_H__
-extern unsigned long long gpu_sim_cycle;
-extern unsigned long long gpu_tot_sim_cycle;
-
namespace Trace {
#define TS_TUP_BEGIN(X) enum X {
@@ -63,17 +60,26 @@ namespace Trace {
#define DPRINTF(x, ...) do {\
if (DTRACE(x)) {\
printf( SIM_PRINT_STR,\
- gpu_sim_cycle + gpu_tot_sim_cycle,\
+ m_gpu->gpu_sim_cycle + m_gpu->gpu_tot_sim_cycle,\
Trace::trace_streams_str[Trace::x] );\
printf(__VA_ARGS__);\
}\
} while (0)
+#define DPRINTFG(x, ...) do {\
+ if (DTRACE(x)) {\
+ printf( SIM_PRINT_STR,\
+ gpu_sim_cycle + gpu_tot_sim_cycle,\
+ Trace::trace_streams_str[Trace::x] );\
+ printf(__VA_ARGS__);\
+ }\
+} while (0)
#else
#define DTRACE(x) (false)
#define DPRINTF(x, ...) do {} while (0)
+#define DPRINTFG(x, ...) do {} while (0)
#endif
diff --git a/version_detection.mk b/version_detection.mk
index 00a86c0..ee71a62 100644
--- a/version_detection.mk
+++ b/version_detection.mk
@@ -33,8 +33,9 @@ GPGPUSIM_VERSION=$(shell cat $(GPGPUSIM_ROOT)/version | awk '/Version/ {print $$
#Detect Git branch and commit #
GIT_COMMIT := $(shell git log -n 1 | head -1 | sed -re 's/commit (.*)/\1/')
-GIT_FILES_CHANGED := $(shell git diff --numstat --cached && git diff --numstat | wc | sed -re 's/^\s+([0-9]+).*/\1/')
-GPGPUSIM_BUILD := "gpgpu-sim_git-commit-$(GIT_COMMIT)_modified_$(GIT_FILES_CHANGED)"
+GIT_FILES_CHANGED_A:=$(shell git diff --numstat | wc | sed -re 's/^\s+([0-9]+).*/\1./')
+GIT_FILES_CHANGED:= $(GIT_FILES_CHANGED_A)$(shell git diff --numstat --cached | wc | sed -re 's/^\s+([0-9]+).*/\1/')
+GPGPUSIM_BUILD := gpgpu-sim_git-commit-$(GIT_COMMIT)_modified_$(GIT_FILES_CHANGED)
endif
# Detect CUDA Runtime Version