summaryrefslogtreecommitdiff
path: root/src/cuda-sim/ptx_parser.cc
diff options
context:
space:
mode:
authorTor Aamodt <[email protected]>2010-08-30 11:05:15 -0800
committerTor Aamodt <[email protected]>2010-08-30 11:05:15 -0800
commitbb820c116764d7a1b8e071137d32b74e7f34dd2f (patch)
tree313d6794087adc13490963b1f847bcc88ccdc0dd /src/cuda-sim/ptx_parser.cc
parent80e1b49ff823190d0316623d414a343575c93eae (diff)
integrating CL 7421-7434 from fermi-test
this integrates the ptxplus functional model changes, but has only been verified with CUDA 3.1 PTX regressions (which pass) still need to verify ptxplus itself is working in this branch [git-p4: depot-paths = "//depot/gpgpu_sim_research/fermi/distribution/": change = 7435]
Diffstat (limited to 'src/cuda-sim/ptx_parser.cc')
-rw-r--r--src/cuda-sim/ptx_parser.cc147
1 files changed, 145 insertions, 2 deletions
diff --git a/src/cuda-sim/ptx_parser.cc b/src/cuda-sim/ptx_parser.cc
index 05ce397..d4a892f 100644
--- a/src/cuda-sim/ptx_parser.cc
+++ b/src/cuda-sim/ptx_parser.cc
@@ -94,6 +94,7 @@ 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;
@@ -165,6 +166,7 @@ void init_instruction_state()
DPRINTF("init_instruction_state");
g_pred = NULL;
g_neg_pred = 0;
+ g_pred_mod = -1;
g_label = NULL;
g_opcode = -1;
g_options.clear();
@@ -291,7 +293,8 @@ void add_instruction()
DPRINTF("add_instruction: %s", ((g_opcode>0)?g_opcode_string[g_opcode]:"<label>") );
ptx_instruction *i = new ptx_instruction( g_opcode,
g_pred,
- g_neg_pred,
+ g_neg_pred,
+ g_pred_mod,
g_label,
g_operands,
g_return_var,
@@ -495,6 +498,21 @@ void add_identifier( const char *identifier, int array_dim, unsigned array_ident
}
}
+void 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);
+ parse_assert( s1 != NULL, "'from' constant identifier does not exist.");
+ parse_assert( s1 != NULL, "'to' constant identifier does not exist.");
+
+ unsigned addr = s2->get_address();
+
+ printf("GPGPU-Sim PTX: moving \"%s\" from 0x%x to 0x%x (%s+%x)\n",
+ identifier1, s1->get_address(), addr+offset, identifier2, offset);
+
+ s1->set_address( addr + offset );
+}
+
void add_function_arg()
{
if( g_func_info ) {
@@ -570,7 +588,7 @@ void add_opcode( int opcode )
g_opcode = opcode;
}
-void add_pred( const char *identifier, int neg )
+void add_pred( const char *identifier, int neg, int predModifier )
{
DPRINTF("add_pred");
const symbol *s = g_current_symbol_table->lookup(identifier);
@@ -580,6 +598,7 @@ void add_pred( const char *identifier, int neg )
}
g_pred = s;
g_neg_pred = neg;
+ g_pred_mod = predModifier;
}
void add_option( int option )
@@ -588,6 +607,19 @@ void add_option( int option )
g_options.push_back( option );
}
+void add_double_operand( const char *d1, const char *d2 )
+{
+ //operands that access two variables.
+ //eg. s[$ofs1+$r0], g[$ofs1+=$r0]
+ //TODO: Not sure if I'm going to use this for storing to two destinations or not.
+
+ DPRINTF("add_double_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, "component(s) missing declarations.");
+ g_operands.push_back( operand_info(s1,s2) );
+}
+
void add_2vector_operand( const char *d1, const char *d2 )
{
DPRINTF("add_2vector_operand");
@@ -631,6 +663,109 @@ void add_memory_operand()
g_operands.back().make_memory_operand();
}
+/*TODO: add other memory locations*/
+void change_memory_addr_space(const char *identifier)
+{
+ /*0 = N/A, not reading from memory
+ *1 = global memory
+ *2 = shared memory
+ *3 = const memory segment
+ *4 = local memory segment
+ */
+
+ bool recognizedType = false;
+
+ DPRINTF("change_memory_addr_space");
+ assert( !g_operands.empty() );
+ if(!strcmp(identifier, "g"))
+ {
+ g_operands.back().set_addr_space(1);
+ recognizedType = true;
+ }
+ if(!strcmp(identifier, "s"))
+ {
+ g_operands.back().set_addr_space(2);
+ recognizedType = true;
+ }
+ // For constants, check if the first character is 'c'
+ char c[2];
+ strncpy(c, identifier, 1); c[1] = '\0';
+ if(!strcmp(c, "c"))
+ {
+ g_operands.back().set_addr_space(3);
+ parse_assert(g_current_symbol_table->lookup(identifier) != NULL, "Constant was not defined.");
+ g_operands.back().set_const_mem_offset(g_current_symbol_table->lookup(identifier)->get_address());
+ recognizedType = true;
+ }
+ // For local memory, check if the first character is 'l'
+ char l[2];
+ strncpy(l, identifier, 1); l[1] = '\0';
+ if(!strcmp(l, "l"))
+ {
+ g_operands.back().set_addr_space(4);
+ parse_assert(g_current_symbol_table->lookup(identifier) != NULL, "Local memory segment was not defined.");
+ g_operands.back().set_const_mem_offset(g_current_symbol_table->lookup(identifier)->get_address());
+ recognizedType = true;
+ }
+
+ parse_assert(recognizedType, "Error: unrecognized memory type.");
+}
+
+void change_operand_lohi( int lohi )
+{
+ /*0 = N/A, read entire operand
+ *1 = lo, reading from lowest bits
+ *2 = hi, reading from highest bits
+ */
+
+ DPRINTF("change_operand_lohi");
+ assert( !g_operands.empty() );
+
+ g_operands.back().set_operand_lohi(lohi);
+
+}
+
+void change_double_operand_type( int operand_type )
+{
+ /*
+ *-3 = reg / reg (set instruction, but both get same value)
+ *-2 = reg | reg (cvt instruction)
+ *-1 = reg | reg (set instruction)
+ *0 = N/A, default
+ *1 = reg + reg
+ *2 = reg += reg
+ *3 = reg += immediate
+ */
+
+ DPRINTF("change_double_operand_type");
+ assert( !g_operands.empty() );
+
+ // For double destination operands, ensure valid instruction
+ if( operand_type == -1 || operand_type == -2 ) {
+ if((g_opcode == SET_OP)||(g_opcode == SETP_OP))
+ g_operands.back().set_double_operand_type(-1);
+ else
+ g_operands.back().set_double_operand_type(-2);
+ } else if( operand_type == -3 ) {
+ if(g_opcode == SET_OP)
+ g_operands.back().set_double_operand_type(operand_type);
+ else
+ parse_assert(0, "Error: Unsupported use of double destination operand.");
+ } else {
+ g_operands.back().set_double_operand_type(operand_type);
+ }
+
+}
+
+void change_operand_neg( )
+{
+ DPRINTF("change_operand_neg");
+ assert( !g_operands.empty() );
+
+ g_operands.back().set_operand_neg();
+
+}
+
void add_literal_int( int value )
{
DPRINTF("add_literal_int");
@@ -741,3 +876,11 @@ void add_pragma( const char *str )
{
printf("GPGPU-Sim PTX: Warning -- ignoring pragma '%s'\n", str );
}
+
+void version_header(double a) {} //intentional dummy function
+void target_header(char* a) {} //intentional dummy function
+void target_header2(char* a, char* b) {} //intentional dummy function
+
+void func_header(char* a) {} //intentional dummy function
+void func_header_info(char* a) {} //intentional dummy function
+void func_header_info_int(char* a, int b) {} //intentional dummy function