def get_thunk_type_set():
it_types = []<EOL>i_types = []<EOL>j = <NUM_LIT:0><EOL>getter_code = "<STR_LIT>"<EOL>for I_typenum, I_type in I_TYPES:<EOL><INDENT>piece = """<STR_LIT>"""<EOL>getter_code += piece % dict(I_typenum=I_typenum, j=j)<EOL>i_types.append((j, I_typenum, None, I_type, None))<EOL>j += <NUM_LIT:1><EOL>for T_typenum, T_type in T_TYPES:<EOL><INDENT>piece = """<STR_LIT>"""<EOL>getter_code += piece % dict(T_typenum=T_typenum, j=j)<EOL>it_types.append((j, I_typenum, T_typenum, I_type, T_type))<EOL>j += <NUM_LIT:1><EOL><DEDENT>getter_code += """<STR_LIT>"""<EOL><DEDENT>return i_types, it_types, GET_THUNK_CASE_TEMPLATE % dict(content=getter_code)<EOL>
Get a list containing cartesian product of data types, plus a getter routine.

Returns
-------
i_types : list [(j, I_typenum, None, I_type, None), ...] 
     Pairing of index type numbers and the corresponding C++ types,
     and an unique index `j`. This is for routines that are parameterized
     only by I but not by T.
it_types : list [(j, I_typenum, T_typenum, I_type, T_type), ...]
     Same as `i_types`, but for routines parameterized both by T and I.
getter_code : str
     C++ code for a function that takes I_typenum, T_typenum and returns
     the unique index corresponding to the lists, or -1 if no match was
     found.