Re: [hatari-devel] WinUAE CPU core cycles issue

[ Thread Index | Date Index | More lists.tuxfamily.org/hatari-devel Archives ]


Hi Eero,

Laurent, is it OK if I add OpcodeFamily updating to 20 & 21 cores,
i.e. for the default Falcon WinUAE CPU core?


Of course it is OK, don't hesitate.

Best regards

Laurent


Le 14/03/2013 11:03, Eero Tamminen a écrit :
Hi,

On torstai 07 maaliskuu 2013, Eero Tamminen wrote:
On keskiviikko 06 maaliskuu 2013, Laurent Sallafranque wrote:
When I added the "accurate cycles" for the 68030, I focused on the
"cycle exact" 68030 CPU, ie cpuemu_31.c
In that case you've unfortunately focused on the wrong file. :-/

As I stated earlier, OpcodeFamily isn't updated for the *default* WinUAE
core.  Only generated cpuemu variants which don't update them are 20 and
21.
Laurent, is it OK if I add OpcodeFamily updating to 20 & 21 cores,
i.e. for the default Falcon WinUAE CPU core?


	- Eero

Default "cycle exact" 030 WinUAE CPU core uses the code from cpuemu_21..c
file, as can be seen from the WinUAE code:
----  src/cpu/newcpu.c ----
...
void build_cpufunctbl (void)
{
...
         switch (currprefs.cpu_model)
         {
...
         case 68030:
                 lvl = 3;
                 tbl = op_smalltbl_2_ff;
                 if (currprefs.cpu_cycle_exact)
                         tbl = op_smalltbl_23_ff;      <=== *****
                 if (currprefs.mmu_model)
                         tbl = op_smalltbl_32_ff;
                 break;
...
---- build/src/cpu/cpustbl.c ----
...
const struct cputbl CPUFUNC(op_smalltbl_23)[] = {     <=== *****
{ (cpuop_func*)CPUFUNC(op_0000_21), 0 }, /* OR */
{ (cpuop_func*)CPUFUNC(op_0010_21), 16 }, /* OR */
...
{ (cpuop_func*)CPUFUNC(op_46fc_21), 18172 }, /* MV2SR */
{ (cpuop_func*)CPUFUNC(op_4800_23), 18432 }, /* NBCD */
{ (cpuop_func*)CPUFUNC(op_4808_21), 18440 }, /* LINK */
{ (cpuop_func*)CPUFUNC(op_4810_23), 18448 }, /* NBCD */
...
-----------------------------------
$ $ for i in src/cpu/cpuemu*.c; do
	echo "$i:"; \
	egrep -e 'op_[0-9a-f]*_21' -e 'op_[0-9a-f]*_23' $i | wc -l; \
done
src/cpu/cpuemu_0.c:
0
src/cpu/cpuemu_11.c:
0
src/cpu/cpuemu_12.c:
0
src/cpu/cpuemu_20.c:
0
src/cpu/cpuemu_21.c:
1893                    <=== *****
src/cpu/cpuemu_31.c:
0
src/cpu/cpuemu_32.c:
0
----------------------------------

It's only with MMU that 31 & 32 variants are used.


In gencpu.c, you can see the code generated specifically for
the 030 "cycle-exact" CPU within "using_ce020 == 2" checks:
------------------------
static void returncycles (const char *s, int cycles)
{
         if (using_ce)
                 return;

         if (using_ce020 == 1)
                 printf ("%sreturn;\n", s);
         else if (using_ce020 == 2) {
                 if (no_return_cycles == true)
                         return;
                 if (instr_table == TABLE_FALCON_CYCLES &&
table_falcon_cycles[instr_index].cache_cycles == 0) {
                         printf ("\tregs.ce030_instr_cycles =
table_falcon_cycles[0];\n");
                 }
                 else {
                         printf ("%s\tregs.ce030_instr_cycles =
%s[%d];\n", s, falcon_cycles_tables[instr_table], instr_table_index);
                 }

                 printf ("%s\treturn;\n", s);
         }
         else
                 printf ("%sreturn %d * CYCLE_UNIT / 2;\n", s, cycles);
}
...
static void genmovemel (uae_u16 opcode), and
static void genmovemle (uae_u16 opcode)
{
...
         if (using_ce020 == 2) {
                 if (table68k[opcode].size == sz_long)
                         printf ("\tregs.ce030_instr_addcycles =
regs_number * 8;\n");
                 else
                         printf ("\tregs.ce030_instr_addcycles =
regs_number * 4;\n");
         }

         fill_prefetch_next ();
}
...
static void gen_opcode (unsigned long int opcode)
{
         struct instr *curi = table68k + opcode;

         insn_n_cycles = using_prefetch ? 0 : 4;

         if (!using_ce020) {
                 printf ("\tOpcodeFamily = %d; CurrentInstrCycles =
\n", curi->mnemo);
                 nCurInstrCycPos = ftell(stdout) - 5;
         }
         else if (using_ce020 == 2) {
                 instr_table = TABLE_FALCON_CYCLES;
                 instr_table_index = instr_index;
                 no_return_cycles = false;
         }

         if (using_ce020) {
                 if (using_ce020 == 2) {
                         ce020_prefetch_long = "get_long_ce030_prefetch";
                         ce020_prefetch_word = "get_word_ce030_prefetch";
                         srcl = "get_long_ce030";
                         dstl = "put_long_ce030";
                         srcw = "get_word_ce030";
                         dstw = "put_word_ce030";
                         srcb = "get_byte_ce030";
                         dstb = "put_byte_ce030";
                 } else {
                         ce020_prefetch_long = "get_long_ce020_prefetch";
                         ce020_prefetch_word = "get_word_ce020_prefetch";
                         srcl = "get_long_ce020";
                         dstl = "put_long_ce020";
                         srcw = "get_word_ce020";
                         dstw = "put_word_ce020";
                         srcb = "get_byte_ce020";
                         dstb = "put_byte_ce020";
                 }
...
         case i_RTS:
                 printf ("\tuaecptr pc = m68k_getpc ();\n");
                 if (using_ce020 == 1)
                         printf ("\tm68k_do_rts_ce020 ();\n");
                 else if (using_ce020 == 2)
                         printf ("\tm68k_do_rts_ce030 ();\n");
...
                 if (using_ce020 == 2) { /* For Falcon cycle exact timings
only (CPU_EMU_21) */
                         if (curi->size == sz_byte)
                                 instr_table_index = 1;
                         else if (curi->size == sz_word)
                                 instr_table_index = 2;
                         else
                                 instr_table_index = 3;
                 }
...
int main (int argc, char **argv)
{
         for (i = 0; i <= 32; i++) {
                 postfix = i;
                 if ((i >= 6 && i < 11) || (i > 12 && i < 20) || (i > 23
&& i < 31))
                         continue;
                 generate_stbl = 1;
// REDUNDANT CHECK, above if already handles this!
                 if (i == 0 || i == 11 || i == 12 || i == 20 || i == 21

                     || i == 31 || i == 32) {

                         if (generate_stbl)
                                 fprintf (stblfile, "#ifdef CPUEMU_%d\n",
postfix);
                         postfix2 = postfix;
                         sprintf (fname, "cpuemu_%d.c", postfix);
                         if (freopen (fname, "wb", stdout) == NULL) {
                                 perror(fname);
                                 return -1;
                         }
                         generate_includes (stdout);
                 }
                 using_mmu = 0;
                 using_prefetch = 0;
                 using_ce = 0;
                 using_ce020 = 0;
                 using_mmu = 0;
                 cpu_level = 5 - i;
                 if (i == 11 || i == 12) {
                         cpu_level = 0;
                         using_prefetch = 1;
                         using_exception_3 = 1;
                         if (i == 12)
                                 using_ce = 1;
                         for (rp = 0; rp < nr_cpuop_funcs; rp++)
                                 opcode_next_clev[rp] = 0;
                 } else if (i == 20) {
                         cpu_level = 2;
                         using_ce020 = 1;
                         read_counts ();
                         for (rp = 0; rp < nr_cpuop_funcs; rp++)
                                 opcode_next_clev[rp] = cpu_level;
                 } else if (i == 21 || i == 22 || i == 23) {
                         cpu_level = 3 + (23 - i);
                         using_ce020 = 2;
                         if (i == 21) {
                                 read_counts ();
                                 for (rp = 0; rp < nr_cpuop_funcs; rp++)
                                         opcode_next_clev[rp] = cpu_level;
                         }
                 } else if (i >= 31 && i < 40) {
                         cpu_level = 3 + 32 - i;
                         using_mmu = 1;
                         if (cpu_level == 3) {
                                 fprintf (stdout, "#include
\"cpummu030.h\"\n");
                                 mmu_postfix = "030";
                         }
                         else {
                                 fprintf (stdout, "#include
\"cpummu.h\"\n"); mmu_postfix = "";
                         }

                         if (i == 31)
                                 read_counts ();
                         for (rp = 0; rp < nr_cpuop_funcs; rp++)
                                 opcode_next_clev[rp] = cpu_level;
                 }
---------
(comments are removed as they make this harder to read)


	- Eero







Mail converted by MHonArc 2.6.19+ http://listengine.tuxfamily.org/