summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--CHANGES4
-rw-r--r--src/abstract_hardware_model.cc32
-rw-r--r--src/abstract_hardware_model.h40
-rw-r--r--src/cuda-sim/cuda-sim.cc37
-rw-r--r--src/cuda-sim/cuda-sim.h15
-rw-r--r--src/cuda-sim/ptx_sim.cc2
-rw-r--r--src/gpgpu-sim/shader.cc11
7 files changed, 89 insertions, 52 deletions
diff --git a/CHANGES b/CHANGES
index cbc929b..88657d1 100644
--- a/CHANGES
+++ b/CHANGES
@@ -25,6 +25,7 @@ Version 3.2.1+edits (development branch) versus 3.2.1
- Added breakdown for interconnection traffic based on memory access type.
- Changes to the makefiles s.t. all intermediate files get output to the build
directory, and nothing is written to the same directory as the source code
+- Implemented the WARPSZ query in CUDA.
- Bug Fixes:
- Fixed the flit count sent to GPUWattch for atomic operations.
- Fix for Bug 51 - Updated the function declaration of
@@ -43,7 +44,8 @@ Version 3.2.1+edits (development branch) versus 3.2.1
- Average/min/max per-kernel powers not being reset at kernel boundaries causing
incorrect per-kernel values.
- Fixed a dependency error in the src/cuda-sim Makefile.
- - Fixing a source of non-determinism in GPGPU-Sim (Bug 147).
+ - Fixing a source of non-determinism in GPGPU-Sim (Bug 147).
+ - Eliminated some memory leaks in the pure functional simulator
Version 3.2.1 versus 3.2.0
- Added kernel name and launch uids to performance statistics log.
diff --git a/src/abstract_hardware_model.cc b/src/abstract_hardware_model.cc
index fd227e1..5ba0270 100644
--- a/src/abstract_hardware_model.cc
+++ b/src/abstract_hardware_model.cc
@@ -746,13 +746,13 @@ void simt_stack::update( simt_mask_t &thread_done, addr_vector_t &next_pc, addre
}
}
-void core_t::execute_warp_inst_t(warp_inst_t &inst, unsigned warpSize, unsigned warpId)
+void core_t::execute_warp_inst_t(warp_inst_t &inst, unsigned warpId)
{
- for ( unsigned t=0; t < warpSize; t++ ) {
+ for ( unsigned t=0; t < m_warp_size; t++ ) {
if( inst.active(t) ) {
if(warpId==(unsigned (-1)))
warpId = inst.warp_id();
- unsigned tid=warpSize*warpId+t;
+ unsigned tid=m_warp_size*warpId+t;
m_thread[tid]->ptx_exec_inst(inst,t);
//virtual function
@@ -766,12 +766,12 @@ bool core_t::ptx_thread_done( unsigned hw_thread_id ) const
return ((m_thread[ hw_thread_id ]==NULL) || m_thread[ hw_thread_id ]->is_done());
}
-void core_t::updateSIMTStack(unsigned warpId, unsigned warpSize, warp_inst_t * inst)
+void core_t::updateSIMTStack(unsigned warpId, warp_inst_t * inst)
{
simt_mask_t thread_done;
addr_vector_t next_pc;
- unsigned wtid = warpId * warpSize;
- for (unsigned i = 0; i < warpSize; i++) {
+ unsigned wtid = warpId * m_warp_size;
+ for (unsigned i = 0; i < m_warp_size; i++) {
if( ptx_thread_done(wtid+i) ) {
thread_done.set(i);
next_pc.push_back( (address_type)-1 );
@@ -794,11 +794,23 @@ warp_inst_t core_t::getExecuteWarp(unsigned warpId)
return wi;
}
-void core_t::initilizeSIMTStack(unsigned warps, unsigned warpsSize)
+void core_t::deleteSIMTStack()
+{
+ if ( m_simt_stack ) {
+ for (unsigned i = 0; i < m_warp_count; ++i)
+ delete m_simt_stack[i];
+ delete[] m_simt_stack;
+ m_simt_stack = NULL;
+ }
+}
+
+void core_t::initilizeSIMTStack(unsigned warp_count, unsigned warp_size)
{
- m_simt_stack = new simt_stack*[warps];
- for (unsigned i = 0; i < warps; ++i)
- m_simt_stack[i] = new simt_stack(i,warpsSize);
+ 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_warp_size = warp_size;
+ m_warp_count = warp_count;
}
void core_t::get_pdom_stack_top_info( unsigned warpId, unsigned *pc, unsigned *rpc ) const
diff --git a/src/abstract_hardware_model.h b/src/abstract_hardware_model.h
index 9a29bc3..883e122 100644
--- a/src/abstract_hardware_model.h
+++ b/src/abstract_hardware_model.h
@@ -29,7 +29,9 @@
#define ABSTRACT_HARDWARE_MODEL_INCLUDED
-
+// Forward declarations
+class gpgpu_sim;
+class kernel_info_t;
enum _memory_space_t {
undefined_space=0,
@@ -964,23 +966,49 @@ size_t get_kernel_code_size( class function_info *entry );
*/
class core_t {
public:
- virtual ~core_t() {}
+ core_t( gpgpu_sim *gpu,
+ kernel_info_t *kernel,
+ unsigned warp_size,
+ unsigned threads_per_shader )
+ : m_gpu( gpu ),
+ m_kernel( kernel ),
+ m_simt_stack( NULL ),
+ m_thread( NULL ),
+ m_warp_size( warp_size )
+ {
+ m_warp_count = threads_per_shader/m_warp_size;
+ // Handle the case where the number of threads is not a
+ // multiple of the warp size
+ if ( threads_per_shader % m_warp_size != 0 ) {
+ m_warp_count += 1;
+ }
+ assert( m_warp_count * m_warp_size > 0 );
+ m_thread = ( ptx_thread_info** )
+ calloc( m_warp_count * m_warp_size,
+ sizeof( ptx_thread_info* ) );
+ initilizeSIMTStack(m_warp_count,m_warp_size);
+ }
+ virtual ~core_t() { free(m_thread); }
virtual void warp_exit( unsigned warp_id ) = 0;
virtual bool warp_waiting_at_barrier( unsigned warp_id ) const = 0;
virtual void checkExecutionStatusAndUpdate(warp_inst_t &inst, unsigned t, unsigned tid)=0;
class gpgpu_sim * get_gpu() {return m_gpu;}
- void execute_warp_inst_t(warp_inst_t &inst, unsigned warpSize, unsigned warpId =(unsigned)-1);
+ void execute_warp_inst_t(warp_inst_t &inst, unsigned warpId =(unsigned)-1);
bool ptx_thread_done( unsigned hw_thread_id ) const ;
- void updateSIMTStack(unsigned warpId, unsigned warpSize, warp_inst_t * inst);
- void initilizeSIMTStack(unsigned warps, unsigned warpsSize);
+ void updateSIMTStack(unsigned warpId, warp_inst_t * inst);
+ void initilizeSIMTStack(unsigned warp_count, unsigned warps_size);
+ void deleteSIMTStack();
warp_inst_t getExecuteWarp(unsigned warpId);
void get_pdom_stack_top_info( unsigned warpId, unsigned *pc, unsigned *rpc ) const;
kernel_info_t * get_kernel_info(){ return m_kernel;}
+ unsigned get_warp_size() const { return m_warp_size; }
protected:
class gpgpu_sim *m_gpu;
kernel_info_t *m_kernel;
simt_stack **m_simt_stack; // pdom based reconvergence context for each warp
- class ptx_thread_info ** m_thread;
+ class ptx_thread_info ** m_thread;
+ unsigned m_warp_size;
+ unsigned m_warp_count;
};
diff --git a/src/cuda-sim/cuda-sim.cc b/src/cuda-sim/cuda-sim.cc
index a7294c1..ef50588 100644
--- a/src/cuda-sim/cuda-sim.cc
+++ b/src/cuda-sim/cuda-sim.cc
@@ -1702,7 +1702,11 @@ void gpgpu_cuda_ptx_sim_main_func( kernel_info_t &kernel, bool openCL )
//we excute the kernel one CTA (Block) at the time, as synchronization functions work block wise
while(!kernel.no_more_ctas_to_run()){
- functionalCoreSim cta(&kernel, g_the_gpu, g_the_gpu->getShaderCoreConfig()->warp_size);
+ functionalCoreSim cta(
+ &kernel,
+ g_the_gpu,
+ g_the_gpu->getShaderCoreConfig()->warp_size
+ );
cta.execute();
}
@@ -1744,27 +1748,22 @@ void gpgpu_cuda_ptx_sim_main_func( kernel_info_t &kernel, bool openCL )
void functionalCoreSim::initializeCTA()
{
int ctaLiveThreads=0;
- m_warpsCount= ceil((double)m_kernel->threads_per_cta()/m_maxWarpSize);
- initilizeSIMTStack(m_warpsCount,m_maxWarpSize);
- m_warpAtBarrier = new bool [m_warpsCount];
- m_liveThreadCount = new unsigned [m_warpsCount];
- m_thread = new ptx_thread_info*[m_warpsCount*m_maxWarpSize];
- for(int i=0; i< m_warpsCount; i++){
+ for(int i=0; i< m_warp_count; i++){
m_warpAtBarrier[i]=false;
m_liveThreadCount[i]=0;
}
- for(int i=0; i< m_warpsCount*m_maxWarpSize;i++)
+ for(int i=0; i< m_warp_count*m_warp_size;i++)
m_thread[i]=NULL;
//get threads for a cta
for(unsigned i=0; i<m_kernel->threads_per_cta();i++) {
- ptx_sim_init_thread(*m_kernel,&m_thread[i],0,i,m_kernel->threads_per_cta()-i,m_kernel->threads_per_cta(),this,0,i/m_maxWarpSize,(gpgpu_t*)m_gpu, true);
+ ptx_sim_init_thread(*m_kernel,&m_thread[i],0,i,m_kernel->threads_per_cta()-i,m_kernel->threads_per_cta(),this,0,i/m_warp_size,(gpgpu_t*)m_gpu, true);
assert(m_thread[i]!=NULL && !m_thread[i]->is_done());
ctaLiveThreads++;
}
- for(int k=0;k<m_warpsCount;k++)
+ for(int k=0;k<m_warp_count;k++)
createWarp(k);
}
@@ -1773,13 +1772,13 @@ void functionalCoreSim::createWarp(unsigned warpId)
simt_mask_t initialMask;
unsigned liveThreadsCount=0;
initialMask.set();
- for(int i=warpId*m_maxWarpSize; i<warpId*m_maxWarpSize+m_maxWarpSize;i++){
- if(m_thread[i]==NULL) initialMask.reset(i-warpId*m_maxWarpSize);
+ for(int i=warpId*m_warp_size; i<warpId*m_warp_size+m_warp_size;i++){
+ if(m_thread[i]==NULL) initialMask.reset(i-warpId*m_warp_size);
else liveThreadsCount++;
}
- assert(m_thread[warpId*m_maxWarpSize]!=NULL);
- m_simt_stack[warpId]->launch(m_thread[warpId*m_maxWarpSize]->get_pc(),initialMask);
+ assert(m_thread[warpId*m_warp_size]!=NULL);
+ m_simt_stack[warpId]->launch(m_thread[warpId*m_warp_size]->get_pc(),initialMask);
m_liveThreadCount[warpId]= liveThreadsCount;
}
@@ -1791,12 +1790,12 @@ void functionalCoreSim::execute()
while(true){
bool someOneLive= false;
bool allAtBarrier = true;
- for(unsigned i=0;i<m_warpsCount;i++){
+ for(unsigned i=0;i<m_warp_count;i++){
executeWarp(i,allAtBarrier,someOneLive);
}
if(!someOneLive) break;
if(allAtBarrier){
- for(unsigned i=0;i<m_warpsCount;i++)
+ for(unsigned i=0;i<m_warp_count;i++)
m_warpAtBarrier[i]=false;
}
}
@@ -1806,10 +1805,10 @@ void functionalCoreSim::executeWarp(unsigned i, bool &allAtBarrier, bool & someO
{
if(!m_warpAtBarrier[i] && m_liveThreadCount[i]!=0){
warp_inst_t inst =getExecuteWarp(i);
- execute_warp_inst_t(inst,m_maxWarpSize,i);
+ execute_warp_inst_t(inst,i);
if(inst.isatomic()) inst.do_atomic(true);
if(inst.op==BARRIER_OP || inst.op==MEMORY_BARRIER_OP ) m_warpAtBarrier[i]=true;
- updateSIMTStack(i,m_maxWarpSize,&inst);
+ updateSIMTStack( i, &inst );
}
if(m_liveThreadCount[i]>0) someOneLive=true;
if(!m_warpAtBarrier[i]&& m_liveThreadCount[i]>0) allAtBarrier = false;
@@ -1989,7 +1988,7 @@ address_type get_converge_point( address_type pc )
void functionalCoreSim::warp_exit( unsigned warp_id )
{
- for(int i=0;i<m_warpsCount*m_maxWarpSize;i++){
+ for(int i=0;i<m_warp_count*m_warp_size;i++){
if(m_thread[i]!=NULL){
m_thread[i]->m_cta_info->register_deleted_thread(m_thread[i]);
delete m_thread[i];
diff --git a/src/cuda-sim/cuda-sim.h b/src/cuda-sim/cuda-sim.h
index 96953fb..4c26350 100644
--- a/src/cuda-sim/cuda-sim.h
+++ b/src/cuda-sim/cuda-sim.h
@@ -85,12 +85,13 @@ void set_param_gpgpu_num_shaders(int num_shaders);
class functionalCoreSim: public core_t
{
public:
- functionalCoreSim(kernel_info_t * kernel, gpgpu_sim *g, unsigned maxwarpSize){
- this->m_kernel=kernel;
- m_gpu=g;
- m_maxWarpSize = maxwarpSize;
+ functionalCoreSim(kernel_info_t * kernel, gpgpu_sim *g, unsigned warp_size)
+ : core_t( g, kernel, warp_size, kernel->threads_per_cta() )
+ {
+ m_warpAtBarrier = new bool [m_warp_count];
+ m_liveThreadCount = new unsigned [m_warp_count];
}
- ~functionalCoreSim(){
+ virtual ~functionalCoreSim(){
warp_exit(0);
delete[] m_liveThreadCount;
delete[] m_warpAtBarrier;
@@ -110,15 +111,13 @@ private:
virtual void checkExecutionStatusAndUpdate(warp_inst_t &inst, unsigned t, unsigned tid)
{
if(m_thread[tid]==NULL || m_thread[tid]->is_done()){
- m_liveThreadCount[tid/m_maxWarpSize]--;
+ m_liveThreadCount[tid/m_warp_size]--;
}
}
// lunches the stack and set the threads count
void createWarp(unsigned warpId);
- unsigned m_maxWarpSize;
- unsigned m_warpsCount;
//each warp live thread count and barrier indicator
unsigned * m_liveThreadCount;
bool* m_warpAtBarrier;
diff --git a/src/cuda-sim/ptx_sim.cc b/src/cuda-sim/ptx_sim.cc
index e969e88..9b32e68 100644
--- a/src/cuda-sim/ptx_sim.cc
+++ b/src/cuda-sim/ptx_sim.cc
@@ -270,7 +270,7 @@ unsigned ptx_thread_info::get_builtin( int builtin_id, unsigned dim_mod )
if( dim_mod == 2 ) return m_tid.z;
abort();
break;
- case WARPSZ_REG: feature_not_implemented( "WARP_SZ" ); return 0;
+ case WARPSZ_REG: return m_core->get_warp_size() ;
default:
assert(0);
}
diff --git a/src/gpgpu-sim/shader.cc b/src/gpgpu-sim/shader.cc
index 830b8c1..e3b1ac5 100644
--- a/src/gpgpu-sim/shader.cc
+++ b/src/gpgpu-sim/shader.cc
@@ -72,11 +72,10 @@ shader_core_ctx::shader_core_ctx( class gpgpu_sim *gpu,
const struct shader_core_config *config,
const struct memory_config *mem_config,
shader_core_stats *stats )
- : m_barriers( config->max_warps_per_shader, config->max_cta_per_core ),
+ : core_t( gpu, NULL, config->warp_size, config->n_thread_per_shader ),
+ m_barriers( config->max_warps_per_shader, config->max_cta_per_core ),
m_dynamic_warp_id(0)
{
- m_kernel = NULL;
- m_gpu = gpu;
m_cluster = cluster;
m_config = config;
m_memory_config = mem_config;
@@ -92,7 +91,6 @@ shader_core_ctx::shader_core_ctx( class gpgpu_sim *gpu,
}
m_threadState = (thread_ctx_t*) calloc(sizeof(thread_ctx_t), config->n_thread_per_shader);
- m_thread = (ptx_thread_info**) calloc(sizeof(ptx_thread_info*), config->n_thread_per_shader);
m_not_completed = 0;
m_active_threads.reset();
@@ -122,7 +120,6 @@ 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));
- initilizeSIMTStack(config->max_warps_per_shader,this->get_config()->warp_size);
m_scoreboard = new Scoreboard(m_sid, m_config->max_warps_per_shader);
//scedulers
@@ -641,7 +638,7 @@ void shader_core_ctx::fetch()
void shader_core_ctx::func_exec_inst( warp_inst_t &inst )
{
- execute_warp_inst_t(inst, m_config->warp_size);
+ execute_warp_inst_t(inst);
if( inst.is_load() || inst.is_store() )
inst.generate_mem_accesses();
}
@@ -662,7 +659,7 @@ void shader_core_ctx::issue_warp( register_set& pipe_reg_set, const warp_inst_t*
else if( next_inst->op == MEMORY_BARRIER_OP )
m_warp[warp_id].set_membar();
- updateSIMTStack(warp_id,m_config->warp_size,*pipe_reg);
+ updateSIMTStack(warp_id,*pipe_reg);
m_scoreboard->reserveRegisters(*pipe_reg);
m_warp[warp_id].set_next_pc(next_inst->pc + next_inst->isize);
}