1 |
/* |
/* |
2 |
* Copyright (C) 2005 Anders Gavare. All rights reserved. |
* Copyright (C) 2005-2006 Anders Gavare. All rights reserved. |
3 |
* |
* |
4 |
* Redistribution and use in source and binary forms, with or without |
* Redistribution and use in source and binary forms, with or without |
5 |
* modification, are permitted provided that the following conditions are met: |
* modification, are permitted provided that the following conditions are met: |
25 |
* SUCH DAMAGE. |
* SUCH DAMAGE. |
26 |
* |
* |
27 |
* |
* |
28 |
* $Id: cpu_alpha_palcode.c,v 1.1 2005/08/29 14:36:41 debug Exp $ |
* $Id: cpu_alpha_palcode.c,v 1.5 2006/01/14 13:15:32 debug Exp $ |
29 |
* |
* |
30 |
* Alpha PALcode-related functionality. |
* Alpha PALcode-related functionality. |
31 |
*/ |
*/ |
86 |
case 0x3c: snprintf(buf, buflen, "PAL_OSF1_whami"); break; |
case 0x3c: snprintf(buf, buflen, "PAL_OSF1_whami"); break; |
87 |
case 0x3d: snprintf(buf, buflen, "PAL_OSF1_retsys"); break; |
case 0x3d: snprintf(buf, buflen, "PAL_OSF1_retsys"); break; |
88 |
case 0x3f: snprintf(buf, buflen, "PAL_OSF1_rti"); break; |
case 0x3f: snprintf(buf, buflen, "PAL_OSF1_rti"); break; |
89 |
|
case 0x81: snprintf(buf, buflen, "PAL_bugchk"); break; |
90 |
case 0x83: snprintf(buf, buflen, "PAL_OSF1_callsys"); break; |
case 0x83: snprintf(buf, buflen, "PAL_OSF1_callsys"); break; |
91 |
case 0x86: snprintf(buf, buflen, "PAL_OSF1_imb"); break; |
case 0x86: snprintf(buf, buflen, "PAL_OSF1_imb"); break; |
92 |
case 0x92: snprintf(buf, buflen, "PAL_OSF1_urti"); break; |
case 0x92: snprintf(buf, buflen, "PAL_OSF1_urti"); break; |
105 |
|
|
106 |
switch (cpu->cd.alpha.r[ALPHA_A0]) { |
switch (cpu->cd.alpha.r[ALPHA_A0]) { |
107 |
case 0x02: |
case 0x02: |
108 |
/* put string. a1 = channel, a2 = ptr to buf, a3 = len */ |
/* puts: a1 = channel, a2 = ptr to buf, a3 = len */ |
109 |
for (addr = cpu->cd.alpha.r[ALPHA_A2]; |
for (addr = cpu->cd.alpha.r[ALPHA_A2]; |
110 |
addr < cpu->cd.alpha.r[ALPHA_A2] + |
addr < cpu->cd.alpha.r[ALPHA_A2] + |
111 |
cpu->cd.alpha.r[ALPHA_A3]; addr ++) { |
cpu->cd.alpha.r[ALPHA_A3]; addr ++) { |
117 |
cpu->cd.alpha.r[ALPHA_V0] = cpu->cd.alpha.r[ALPHA_A3]; |
cpu->cd.alpha.r[ALPHA_V0] = cpu->cd.alpha.r[ALPHA_A3]; |
118 |
break; |
break; |
119 |
case 0x22: |
case 0x22: |
120 |
|
/* getenv */ |
121 |
fatal("[ Alpha PALcode: GXemul PROM call 0x22: TODO ]\n"); |
fatal("[ Alpha PALcode: GXemul PROM call 0x22: TODO ]\n"); |
122 |
break; |
break; |
123 |
default:fatal("[ Alpha PALcode: GXemul PROM call, a0=0x%llx ]\n", |
default:fatal("[ Alpha PALcode: GXemul PROM call, a0=0x%llx ]\n", |
134 |
* alpha_palcode(): |
* alpha_palcode(): |
135 |
* |
* |
136 |
* Execute an Alpha PALcode instruction. (Most of these correspond to |
* Execute an Alpha PALcode instruction. (Most of these correspond to |
137 |
* NetBSD/alpha code). |
* OSF1 palcodes, used by for example NetBSD/alpha.) |
138 |
*/ |
*/ |
139 |
void alpha_palcode(struct cpu *cpu, uint32_t palcode) |
void alpha_palcode(struct cpu *cpu, uint32_t palcode) |
140 |
{ |
{ |
149 |
/* Floating point enable: a0 = 1 or 0. */ |
/* Floating point enable: a0 = 1 or 0. */ |
150 |
/* TODO */ |
/* TODO */ |
151 |
break; |
break; |
152 |
|
case 0x31: /* PAL_OSF1_wrval */ |
153 |
|
/* a0 = value */ |
154 |
|
cpu->cd.alpha.sysvalue = cpu->cd.alpha.r[ALPHA_A0]; |
155 |
|
break; |
156 |
|
case 0x32: /* PAL_OSF1_rdval */ |
157 |
|
/* return: v0 = value */ |
158 |
|
cpu->cd.alpha.r[ALPHA_V0] = cpu->cd.alpha.sysvalue; |
159 |
|
break; |
160 |
case 0x33: /* PAL_OSF1_tbi */ |
case 0x33: /* PAL_OSF1_tbi */ |
161 |
/* a0 = op, a1 = vaddr */ |
/* a0 = op, a1 = vaddr */ |
162 |
debug("[ Alpha PALcode: PAL_OSF1_tbi: a0=%lli a1=0x%llx ]\n", |
debug("[ Alpha PALcode: PAL_OSF1_tbi: a0=%lli a1=0x%llx ]\n", |
190 |
/* Returns CPU id in v0: */ |
/* Returns CPU id in v0: */ |
191 |
cpu->cd.alpha.r[ALPHA_V0] = cpu->cpu_id; |
cpu->cd.alpha.r[ALPHA_V0] = cpu->cpu_id; |
192 |
break; |
break; |
193 |
|
case 0x81: /* PAL_bugchk */ |
194 |
|
cpu->running = 0; |
195 |
|
break; |
196 |
case 0x83: /* PAL_OSF1_syscall */ |
case 0x83: /* PAL_OSF1_syscall */ |
197 |
if (cpu->machine->userland_emul != NULL) |
if (cpu->machine->userland_emul != NULL) |
198 |
useremul_syscall(cpu, 0); |
useremul_syscall(cpu, 0); |