@designliquido/delegua 1.26.2 → 1.27.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (95) hide show
  1. package/README.md +7 -3
  2. package/avaliador-sintatico/avaliador-sintatico.d.ts +25 -0
  3. package/avaliador-sintatico/avaliador-sintatico.d.ts.map +1 -1
  4. package/avaliador-sintatico/avaliador-sintatico.js +95 -6
  5. package/avaliador-sintatico/avaliador-sintatico.js.map +1 -1
  6. package/bin/package.json +1 -1
  7. package/interfaces/simbolo-interface.d.ts +1 -0
  8. package/interfaces/simbolo-interface.d.ts.map +1 -1
  9. package/interpretador/interpretador.d.ts +1 -1
  10. package/interpretador/interpretador.d.ts.map +1 -1
  11. package/interpretador/interpretador.js +12 -3
  12. package/interpretador/interpretador.js.map +1 -1
  13. package/lexador/lexador-base.d.ts +1 -1
  14. package/lexador/lexador-base.d.ts.map +1 -1
  15. package/lexador/lexador-base.js +2 -2
  16. package/lexador/lexador-base.js.map +1 -1
  17. package/lexador/lexador.d.ts +1 -1
  18. package/lexador/lexador.d.ts.map +1 -1
  19. package/lexador/lexador.js +3 -3
  20. package/lexador/lexador.js.map +1 -1
  21. package/lexador/simbolo.d.ts +2 -1
  22. package/lexador/simbolo.d.ts.map +1 -1
  23. package/lexador/simbolo.js +2 -1
  24. package/lexador/simbolo.js.map +1 -1
  25. package/package.json +1 -1
  26. package/tradutores/index.d.ts +0 -4
  27. package/tradutores/index.d.ts.map +1 -1
  28. package/tradutores/index.js +0 -4
  29. package/tradutores/index.js.map +1 -1
  30. package/tradutores/tradutor-elixir.d.ts +17 -0
  31. package/tradutores/tradutor-elixir.d.ts.map +1 -1
  32. package/tradutores/tradutor-elixir.js +82 -2
  33. package/tradutores/tradutor-elixir.js.map +1 -1
  34. package/tradutores/tradutor-javascript.d.ts.map +1 -1
  35. package/tradutores/tradutor-javascript.js +5 -0
  36. package/tradutores/tradutor-javascript.js.map +1 -1
  37. package/tradutores/tradutor-python.d.ts.map +1 -1
  38. package/tradutores/tradutor-python.js +5 -0
  39. package/tradutores/tradutor-python.js.map +1 -1
  40. package/tradutores/tradutor-ruby.d.ts.map +1 -1
  41. package/tradutores/tradutor-ruby.js +5 -0
  42. package/tradutores/tradutor-ruby.js.map +1 -1
  43. package/umd/delegua.js +457 -4800
  44. package/tradutores/tradutor-assembly-arm.d.ts +0 -98
  45. package/tradutores/tradutor-assembly-arm.d.ts.map +0 -1
  46. package/tradutores/tradutor-assembly-arm.js +0 -711
  47. package/tradutores/tradutor-assembly-arm.js.map +0 -1
  48. package/tradutores/tradutor-assembly-risc-v.d.ts +0 -100
  49. package/tradutores/tradutor-assembly-risc-v.d.ts.map +0 -1
  50. package/tradutores/tradutor-assembly-risc-v.js +0 -688
  51. package/tradutores/tradutor-assembly-risc-v.js.map +0 -1
  52. package/tradutores/tradutor-assembly-x64.d.ts +0 -17
  53. package/tradutores/tradutor-assembly-x64.d.ts.map +0 -1
  54. package/tradutores/tradutor-assembly-x64.js +0 -38
  55. package/tradutores/tradutor-assembly-x64.js.map +0 -1
  56. package/tradutores/tradutor-webassembly.d.ts +0 -159
  57. package/tradutores/tradutor-webassembly.d.ts.map +0 -1
  58. package/tradutores/tradutor-webassembly.js +0 -886
  59. package/tradutores/tradutor-webassembly.js.map +0 -1
  60. package/tradutores/x64/alocador-registradores.d.ts +0 -29
  61. package/tradutores/x64/alocador-registradores.d.ts.map +0 -1
  62. package/tradutores/x64/alocador-registradores.js +0 -192
  63. package/tradutores/x64/alocador-registradores.js.map +0 -1
  64. package/tradutores/x64/codegen.d.ts +0 -43
  65. package/tradutores/x64/codegen.d.ts.map +0 -1
  66. package/tradutores/x64/codegen.js +0 -416
  67. package/tradutores/x64/codegen.js.map +0 -1
  68. package/tradutores/x64/dessa.d.ts +0 -9
  69. package/tradutores/x64/dessa.d.ts.map +0 -1
  70. package/tradutores/x64/dessa.js +0 -124
  71. package/tradutores/x64/dessa.js.map +0 -1
  72. package/tradutores/x64/dominancia.d.ts +0 -25
  73. package/tradutores/x64/dominancia.d.ts.map +0 -1
  74. package/tradutores/x64/dominancia.js +0 -129
  75. package/tradutores/x64/dominancia.js.map +0 -1
  76. package/tradutores/x64/ir.d.ts +0 -144
  77. package/tradutores/x64/ir.d.ts.map +0 -1
  78. package/tradutores/x64/ir.js +0 -44
  79. package/tradutores/x64/ir.js.map +0 -1
  80. package/tradutores/x64/liveness.d.ts +0 -12
  81. package/tradutores/x64/liveness.d.ts.map +0 -1
  82. package/tradutores/x64/liveness.js +0 -159
  83. package/tradutores/x64/liveness.js.map +0 -1
  84. package/tradutores/x64/lowering.d.ts +0 -7
  85. package/tradutores/x64/lowering.d.ts.map +0 -1
  86. package/tradutores/x64/lowering.js +0 -904
  87. package/tradutores/x64/lowering.js.map +0 -1
  88. package/tradutores/x64/ssa.d.ts +0 -9
  89. package/tradutores/x64/ssa.d.ts.map +0 -1
  90. package/tradutores/x64/ssa.js +0 -170
  91. package/tradutores/x64/ssa.js.map +0 -1
  92. package/tradutores/x64/tipos-x64.d.ts +0 -12
  93. package/tradutores/x64/tipos-x64.d.ts.map +0 -1
  94. package/tradutores/x64/tipos-x64.js +0 -59
  95. package/tradutores/x64/tipos-x64.js.map +0 -1
@@ -1,688 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.TradutorAssemblyRISCV = void 0;
4
- const construtos_1 = require("../construtos");
5
- const declaracoes_1 = require("../declaracoes");
6
- class TradutorAssemblyRISCV {
7
- constructor(alvo = 'linux-rv64') {
8
- this.alvo = alvo;
9
- this.indentacao = 0;
10
- this.contadorLabels = 0;
11
- this.variaveis = new Map();
12
- // s2-s9 são callee-saved — seguros para usar como scratch entre chamadas
13
- this.registradoresDisponiveis = ['s2', 's3', 's4', 's5', 's6', 's7', 's8', 's9'];
14
- this.pilhaRegistradores = [];
15
- this.bss = '.bss\n';
16
- this.data = '.data\n';
17
- this.dicionarioConstrutos = {
18
- AcessoIndiceVariavel: this.traduzirAcessoIndiceVariavel.bind(this),
19
- AcessoMetodoOuPropriedade: this.traduzirConstrutoAcessoMetodo.bind(this),
20
- Agrupamento: this.traduzirConstrutoAgrupamento.bind(this),
21
- AtribuicaoPorIndice: this.traduzirConstrutoAtribuicaoPorIndice.bind(this),
22
- Atribuir: this.traduzirConstrutoAtribuir.bind(this),
23
- Binario: this.traduzirConstrutoBinario.bind(this),
24
- Chamada: this.traduzirConstrutoChamada.bind(this),
25
- DefinirValor: this.traduzirConstrutoDefinirValor.bind(this),
26
- FuncaoConstruto: this.traduzirFuncaoConstruto.bind(this),
27
- Isto: () => 'this',
28
- Literal: this.traduzirConstrutoLiteral.bind(this),
29
- Logico: this.traduzirConstrutoLogico.bind(this),
30
- TipoDe: this.traduzirConstrutoTipoDe.bind(this),
31
- Unario: this.traduzirConstrutoUnario.bind(this),
32
- Variavel: this.traduzirConstrutoVariavel.bind(this),
33
- Vetor: this.traduzirConstrutoVetor.bind(this),
34
- };
35
- this.dicionarioDeclaracoes = {
36
- Bloco: this.traduzirDeclaracaoBloco.bind(this),
37
- Enquanto: this.traduzirDeclaracaoEnquanto.bind(this),
38
- Continua: () => 'j .continue_label',
39
- Escolha: this.traduzirDeclaracaoEscolha.bind(this),
40
- Escreva: this.traduzirDeclaracaoEscreva.bind(this),
41
- Expressao: this.traduzirDeclaracaoExpressao.bind(this),
42
- Fazer: this.traduzirDeclaracaoFazer.bind(this),
43
- Falhar: this.traduzirDeclaracaoFalhar.bind(this),
44
- FuncaoDeclaracao: this.traduzirDeclaracaoFuncao.bind(this),
45
- Importar: this.traduzirDeclaracaoImportar.bind(this),
46
- Leia: this.traduzirDeclaracaoLeia.bind(this),
47
- Para: this.traduzirDeclaracaoPara.bind(this),
48
- ParaCada: this.traduzirDeclaracaoParaCada.bind(this),
49
- Retorna: this.traduzirDeclaracaoRetorna.bind(this),
50
- Se: this.traduzirDeclaracaoSe.bind(this),
51
- Sustar: () => 'j .break_label',
52
- Classe: this.traduzirDeclaracaoClasse.bind(this),
53
- Tente: this.traduzirDeclaracaoTente.bind(this),
54
- Const: this.traduzirDeclaracaoConst.bind(this),
55
- Var: this.traduzirDeclaracaoVar.bind(this),
56
- };
57
- this.indentacao = 0;
58
- this.text = `
59
- .text
60
- .global _start
61
-
62
- _start:`;
63
- }
64
- gerarDigitoAleatorio() {
65
- let result = '';
66
- const digits = '0123456789';
67
- for (let i = 0; i < 5; i++) {
68
- const randomIndex = Math.floor(Math.random() * digits.length);
69
- result += digits.charAt(randomIndex);
70
- }
71
- return result;
72
- }
73
- gerarLabel() {
74
- return `.L${this.contadorLabels++}`;
75
- }
76
- obterRegistrador() {
77
- if (this.registradoresDisponiveis.length > 0) {
78
- const reg = this.registradoresDisponiveis.pop();
79
- this.pilhaRegistradores.push(reg);
80
- return reg;
81
- }
82
- return 'a0'; // fallback
83
- }
84
- liberarRegistrador(reg) {
85
- const index = this.pilhaRegistradores.indexOf(reg);
86
- if (index > -1) {
87
- this.pilhaRegistradores.splice(index, 1);
88
- this.registradoresDisponiveis.push(reg);
89
- }
90
- }
91
- // Emite a instrução de carga correta para o registrador destino.
92
- // RISC-V não tem um `ldr reg, =value` polimórfico como ARM —
93
- // usa `li` para inteiros e `la` para endereços de símbolos.
94
- emitirCarga(registrador, valor) {
95
- if (valor === registrador)
96
- return;
97
- if (valor === 'null') {
98
- this.text += `\n li ${registrador}, 0`;
99
- }
100
- else if (/^-?\d+$/.test(valor) || valor === 'true' || valor === 'false') {
101
- const numVal = valor === 'true' ? '1' : valor === 'false' ? '0' : valor;
102
- this.text += `\n li ${registrador}, ${numVal}`;
103
- }
104
- else if (/^-?\d+\.\d+$/.test(valor)) {
105
- // Ponto flutuante: armazenar em .data e carregar endereço.
106
- // Operações FPU não são suportadas por esta implementação básica.
107
- const floatLabel = `float_${this.gerarDigitoAleatorio()}`;
108
- this.data += ` ${floatLabel}: .double ${valor}\n`;
109
- this.text += `\n la ${registrador}, ${floatLabel}`;
110
- }
111
- else {
112
- this.text += `\n la ${registrador}, ${valor}`;
113
- }
114
- }
115
- // Implementação dos Construtos
116
- traduzirAcessoIndiceVariavel(construto) {
117
- let nomeVar;
118
- if (construto.entidadeChamada instanceof construtos_1.Variavel) {
119
- nomeVar = construto.entidadeChamada.simbolo?.lexema;
120
- }
121
- if (!nomeVar)
122
- nomeVar = 'unknown';
123
- const indice = this.dicionarioConstrutos[construto.indice.constructor.name](construto.indice);
124
- const reg = this.obterRegistrador();
125
- this.text += `\n la ${reg}, ${nomeVar}`;
126
- this.emitirCarga('a0', indice);
127
- this.text += `
128
- slli a0, a0, 3 # multiplicar índice por 8 (palavra de 64 bits)
129
- add ${reg}, ${reg}, a0
130
- ld a0, 0(${reg})`;
131
- this.liberarRegistrador(reg);
132
- return 'a0';
133
- }
134
- traduzirConstrutoAcessoMetodo(construto) {
135
- const objeto = this.dicionarioConstrutos[construto.objeto.constructor.name](construto.objeto);
136
- return `${objeto}_${construto.nomeMetodo}`;
137
- }
138
- traduzirConstrutoAgrupamento(construto) {
139
- return this.dicionarioConstrutos[construto.expressao.constructor.name](construto.expressao);
140
- }
141
- traduzirConstrutoAtribuicaoPorIndice(construto) {
142
- let nomeVar;
143
- if (construto.objeto instanceof construtos_1.Variavel) {
144
- nomeVar = construto.objeto.simbolo?.lexema;
145
- }
146
- if (!nomeVar)
147
- nomeVar = 'unknown';
148
- const indice = this.dicionarioConstrutos[construto.indice.constructor.name](construto.indice);
149
- const valor = this.dicionarioConstrutos[construto.valor.constructor.name](construto.valor);
150
- const reg = this.obterRegistrador();
151
- this.text += `\n la ${reg}, ${nomeVar}`;
152
- this.emitirCarga('a1', indice);
153
- this.text += `
154
- slli a1, a1, 3 # multiplicar índice por 8
155
- add ${reg}, ${reg}, a1`;
156
- this.emitirCarga('a1', valor);
157
- this.text += `\n sd a1, 0(${reg})`;
158
- this.liberarRegistrador(reg);
159
- }
160
- traduzirConstrutoAtribuir(construto) {
161
- let nomeVar;
162
- if (construto.alvo instanceof construtos_1.Variavel) {
163
- nomeVar = construto.alvo.simbolo?.lexema;
164
- }
165
- if (!nomeVar)
166
- return;
167
- const valor = this.dicionarioConstrutos[construto.valor.constructor.name](construto.valor);
168
- if (!this.variaveis.has(nomeVar)) {
169
- const varLabel = `var_${nomeVar}`;
170
- this.bss += ` ${varLabel}: .space 8\n`;
171
- this.variaveis.set(nomeVar, varLabel);
172
- }
173
- this.emitirCarga('a0', valor);
174
- this.text += `
175
- la a1, ${this.variaveis.get(nomeVar)}
176
- sd a0, 0(a1)`;
177
- }
178
- traduzirConstrutoBinario(construto) {
179
- const esquerda = this.dicionarioConstrutos[construto.esquerda.constructor.name](construto.esquerda);
180
- const direita = this.dicionarioConstrutos[construto.direita.constructor.name](construto.direita);
181
- const operador = construto.operador.lexema;
182
- const reg = this.obterRegistrador();
183
- // Carregar operando esquerdo em a0
184
- if (esquerda !== 'a0') {
185
- this.emitirCarga('a0', esquerda);
186
- }
187
- // Carregar operando direito no registrador scratch
188
- this.emitirCarga(reg, direita);
189
- switch (operador) {
190
- case '+':
191
- this.text += `\n add a0, a0, ${reg}`;
192
- break;
193
- case '-':
194
- this.text += `\n sub a0, a0, ${reg}`;
195
- break;
196
- case '*':
197
- this.text += `\n mul a0, a0, ${reg}`;
198
- break;
199
- case '/':
200
- this.text += `\n div a0, a0, ${reg}`;
201
- break;
202
- case '%':
203
- // `rem` é instrução única na extensão M (universal em rv64 Linux)
204
- this.text += `\n rem a0, a0, ${reg}`;
205
- break;
206
- case '<':
207
- // slt: a0 = 1 se a0 < reg
208
- this.text += `\n slt a0, a0, ${reg}`;
209
- break;
210
- case '>':
211
- // slt com operandos trocados: a0 = 1 se reg < a0, i.e., a0 > reg
212
- this.text += `\n slt a0, ${reg}, a0`;
213
- break;
214
- case '<=':
215
- // NOT(a0 > reg) = NOT(reg < a0)
216
- this.text += `\n slt a0, ${reg}, a0\n xori a0, a0, 1`;
217
- break;
218
- case '>=':
219
- // NOT(a0 < reg)
220
- this.text += `\n slt a0, a0, ${reg}\n xori a0, a0, 1`;
221
- break;
222
- case '==':
223
- case '===':
224
- // sub + seqz: a0 = 1 se a0 - reg == 0
225
- this.text += `\n sub a0, a0, ${reg}\n seqz a0, a0`;
226
- break;
227
- case '!=':
228
- case '!==':
229
- // sub + snez: a0 = 1 se a0 - reg != 0
230
- this.text += `\n sub a0, a0, ${reg}\n snez a0, a0`;
231
- break;
232
- default:
233
- this.text += `\n # Operador ${operador} não implementado`;
234
- }
235
- this.liberarRegistrador(reg);
236
- return 'a0';
237
- }
238
- traduzirConstrutoChamada(construto) {
239
- let nomeFuncao = 'funcao';
240
- if (construto.entidadeChamada instanceof construtos_1.Variavel) {
241
- nomeFuncao = construto.entidadeChamada.simbolo?.lexema || 'funcao';
242
- }
243
- // Convenção RISC-V: a0-a7 para até 8 argumentos
244
- const registrosArgs = ['a0', 'a1', 'a2', 'a3', 'a4', 'a5', 'a6', 'a7'];
245
- construto.argumentos.forEach((argumento, indice) => {
246
- if (indice < registrosArgs.length) {
247
- const valorArg = this.dicionarioConstrutos[argumento.constructor.name](argumento);
248
- if (valorArg !== registrosArgs[indice]) {
249
- this.emitirCarga(registrosArgs[indice], valorArg);
250
- }
251
- }
252
- });
253
- this.text += `\n call ${nomeFuncao}`;
254
- }
255
- traduzirConstrutoDefinirValor(construto) {
256
- const objeto = this.dicionarioConstrutos[construto.objeto.constructor.name](construto.objeto);
257
- const valor = this.dicionarioConstrutos[construto.valor.constructor.name](construto.valor);
258
- this.emitirCarga('a0', valor);
259
- this.text += `
260
- la a1, ${objeto}
261
- sd a0, 0(a1)`;
262
- }
263
- traduzirFuncaoConstruto(construto) {
264
- const labelFuncao = `func_${this.gerarDigitoAleatorio()}`;
265
- this.text += `
266
-
267
- ${labelFuncao}:
268
- addi sp, sp, -16
269
- sd ra, 8(sp)
270
- sd s0, 0(sp)
271
- addi s0, sp, 16`;
272
- if (construto.corpo && Array.isArray(construto.corpo)) {
273
- construto.corpo.forEach((declaracao) => {
274
- if (this.dicionarioDeclaracoes[declaracao.constructor.name]) {
275
- this.dicionarioDeclaracoes[declaracao.constructor.name](declaracao);
276
- }
277
- });
278
- }
279
- this.text += `
280
- ld ra, 8(sp)
281
- ld s0, 0(sp)
282
- addi sp, sp, 16
283
- ret`;
284
- }
285
- traduzirConstrutoLiteral(construto) {
286
- if (typeof construto.valor === 'string') {
287
- return this.criarStringLiteral(construto);
288
- }
289
- if (typeof construto.valor === 'number' &&
290
- Number.isFinite(construto.valor) &&
291
- !Number.isInteger(construto.valor)) {
292
- return this.criarLiteralPontoFlutuante(construto.valor);
293
- }
294
- return String(construto.valor);
295
- }
296
- traduzirConstrutoLogico(construto) {
297
- const esquerda = this.dicionarioConstrutos[construto.esquerda.constructor.name](construto.esquerda);
298
- const direita = this.dicionarioConstrutos[construto.direita.constructor.name](construto.direita);
299
- const operador = construto.operador.lexema;
300
- const labelVerdadeiro = this.gerarLabel();
301
- const labelFim = this.gerarLabel();
302
- this.emitirCarga('a0', esquerda);
303
- if (operador === 'e' || operador === '&&') {
304
- this.text += `\n beqz a0, ${labelFim}`;
305
- this.emitirCarga('a0', direita);
306
- this.text += `
307
- beqz a0, ${labelFim}
308
- ${labelVerdadeiro}:
309
- li a0, 1
310
- ${labelFim}:`;
311
- }
312
- else if (operador === 'ou' || operador === '||') {
313
- this.text += `\n bnez a0, ${labelVerdadeiro}`;
314
- this.emitirCarga('a0', direita);
315
- this.text += `
316
- bnez a0, ${labelVerdadeiro}
317
- li a0, 0
318
- j ${labelFim}
319
- ${labelVerdadeiro}:
320
- li a0, 1
321
- ${labelFim}:`;
322
- }
323
- return 'a0';
324
- }
325
- traduzirConstrutoTipoDe(construto) {
326
- return this.dicionarioConstrutos[construto.valor.constructor.name](construto.valor);
327
- }
328
- traduzirConstrutoUnario(construto) {
329
- const operando = this.dicionarioConstrutos[construto.operando.constructor.name](construto.operando);
330
- const operador = construto.operador.lexema;
331
- this.emitirCarga('a0', operando);
332
- if (operador === '-') {
333
- this.text += `\n neg a0, a0`;
334
- }
335
- else if (operador === '!' || operador === 'nao') {
336
- // seqz: a0 = 1 se a0 == 0, else 0
337
- this.text += `\n seqz a0, a0`;
338
- }
339
- return 'a0';
340
- }
341
- traduzirConstrutoVariavel(construto) {
342
- const nomeVar = construto.simbolo?.lexema;
343
- if (nomeVar && this.variaveis.has(nomeVar)) {
344
- const varLabel = this.variaveis.get(nomeVar);
345
- this.text += `
346
- la a0, ${varLabel}
347
- ld a0, 0(a0)`;
348
- return 'a0';
349
- }
350
- return nomeVar || 'unknown';
351
- }
352
- traduzirConstrutoVetor(construto) {
353
- const labelVetor = `vetor_${this.gerarDigitoAleatorio()}`;
354
- // `elementos` filtra nós sintáticos (Separador, ComentarioComoConstruto)
355
- const elementos = construto.elementos;
356
- // Cada elemento ocupa 8 bytes em rv64
357
- this.bss += ` ${labelVetor}: .space ${elementos.length * 8}\n`;
358
- elementos.forEach((valor, index) => {
359
- if (this.dicionarioConstrutos[valor.constructor.name]) {
360
- const valorTraduzido = this.dicionarioConstrutos[valor.constructor.name](valor);
361
- this.emitirCarga('a0', valorTraduzido);
362
- this.text += `
363
- la a1, ${labelVetor}
364
- sd a0, ${index * 8}(a1)`;
365
- }
366
- });
367
- return labelVetor;
368
- }
369
- // Implementação das Declarações
370
- traduzirDeclaracaoBloco(declaracao) {
371
- if (declaracao.declaracoes && Array.isArray(declaracao.declaracoes)) {
372
- declaracao.declaracoes.forEach((decl) => {
373
- if (this.dicionarioDeclaracoes[decl.constructor.name]) {
374
- this.dicionarioDeclaracoes[decl.constructor.name](decl);
375
- }
376
- });
377
- }
378
- }
379
- traduzirDeclaracaoEnquanto(declaracao) {
380
- const labelInicio = this.gerarLabel();
381
- const labelFim = this.gerarLabel();
382
- this.text += `\n${labelInicio}:`;
383
- const condicao = this.dicionarioConstrutos[declaracao.condicao.constructor.name](declaracao.condicao);
384
- if (condicao !== 'a0') {
385
- this.emitirCarga('a0', condicao);
386
- }
387
- this.text += `\n beqz a0, ${labelFim}`;
388
- if (this.dicionarioDeclaracoes[declaracao.corpo.constructor.name]) {
389
- this.dicionarioDeclaracoes[declaracao.corpo.constructor.name](declaracao.corpo);
390
- }
391
- this.text += `
392
- j ${labelInicio}
393
- ${labelFim}:`;
394
- }
395
- traduzirDeclaracaoEscolha(declaracao) {
396
- const labelFim = this.gerarLabel();
397
- const valorEscolha = this.dicionarioConstrutos[declaracao.identificadorOuLiteral.constructor.name](declaracao.identificadorOuLiteral);
398
- if (declaracao.caminhos && Array.isArray(declaracao.caminhos)) {
399
- declaracao.caminhos.forEach((caminho) => {
400
- const labelProximo = this.gerarLabel();
401
- if (caminho.condicoes && caminho.condicoes[0]) {
402
- const valorCaso = this.dicionarioConstrutos[caminho.condicoes[0].constructor.name](caminho.condicoes[0]);
403
- this.emitirCarga('a0', valorEscolha);
404
- this.emitirCarga('a1', valorCaso);
405
- this.text += `\n bne a0, a1, ${labelProximo}`;
406
- if (caminho.declaracoes && Array.isArray(caminho.declaracoes)) {
407
- caminho.declaracoes.forEach((decl) => {
408
- if (this.dicionarioDeclaracoes[decl.constructor.name]) {
409
- this.dicionarioDeclaracoes[decl.constructor.name](decl);
410
- }
411
- });
412
- }
413
- this.text += `
414
- j ${labelFim}
415
- ${labelProximo}:`;
416
- }
417
- });
418
- }
419
- this.text += `\n${labelFim}:`;
420
- }
421
- traduzirDeclaracaoExpressao(declaracao) {
422
- if (declaracao.expressao &&
423
- this.dicionarioConstrutos[declaracao.expressao.constructor.name]) {
424
- const resultado = this.dicionarioConstrutos[declaracao.expressao.constructor.name](declaracao.expressao);
425
- if (typeof resultado === 'string' && resultado && resultado !== 'a0') {
426
- this.emitirCarga('a0', resultado);
427
- }
428
- }
429
- }
430
- traduzirDeclaracaoFazer(declaracao) {
431
- const labelInicio = this.gerarLabel();
432
- this.text += `\n${labelInicio}:`;
433
- if (declaracao.caminhoFazer && declaracao.caminhoFazer.declaracoes) {
434
- declaracao.caminhoFazer.declaracoes.forEach((decl) => {
435
- if (this.dicionarioDeclaracoes[decl.constructor.name]) {
436
- this.dicionarioDeclaracoes[decl.constructor.name](decl);
437
- }
438
- });
439
- }
440
- if (declaracao.condicaoEnquanto) {
441
- const condicao = this.dicionarioConstrutos[declaracao.condicaoEnquanto.constructor.name](declaracao.condicaoEnquanto);
442
- if (condicao !== 'a0') {
443
- this.emitirCarga('a0', condicao);
444
- }
445
- this.text += `\n bnez a0, ${labelInicio}`;
446
- }
447
- }
448
- traduzirDeclaracaoFalhar(declaracao) {
449
- let mensagem = '"Erro"';
450
- if (declaracao.explicacao &&
451
- typeof declaracao.explicacao === 'object' &&
452
- 'constructor' in declaracao.explicacao) {
453
- const explicacao = declaracao.explicacao;
454
- if (explicacao.constructor && this.dicionarioConstrutos[explicacao.constructor.name]) {
455
- mensagem = this.dicionarioConstrutos[explicacao.constructor.name](explicacao);
456
- }
457
- }
458
- this.text += `
459
- # Falhar com mensagem: ${mensagem}
460
- li a0, 1
461
- li a7, 93 # sys_exit
462
- ecall`;
463
- }
464
- traduzirDeclaracaoFuncao(declaracao) {
465
- const nomeFuncao = declaracao.simbolo?.lexema || 'funcao';
466
- this.text += `
467
-
468
- ${nomeFuncao}:
469
- addi sp, sp, -16
470
- sd ra, 8(sp)
471
- sd s0, 0(sp)
472
- addi s0, sp, 16`;
473
- if (declaracao.funcao &&
474
- declaracao.funcao.corpo &&
475
- Array.isArray(declaracao.funcao.corpo)) {
476
- declaracao.funcao.corpo.forEach((decl) => {
477
- if (this.dicionarioDeclaracoes[decl.constructor.name]) {
478
- this.dicionarioDeclaracoes[decl.constructor.name](decl);
479
- }
480
- });
481
- }
482
- this.text += `
483
- ld ra, 8(sp)
484
- ld s0, 0(sp)
485
- addi sp, sp, 16
486
- ret`;
487
- }
488
- traduzirDeclaracaoImportar(declaracao) {
489
- this.text += `\n # Importar: ${declaracao.caminho || 'unknown'}`;
490
- }
491
- traduzirDeclaracaoLeia(declaracao) {
492
- let nomeVar;
493
- if (declaracao.argumentos &&
494
- declaracao.argumentos[0] &&
495
- declaracao.argumentos[0] instanceof construtos_1.Variavel) {
496
- nomeVar = declaracao.argumentos[0].simbolo?.lexema;
497
- }
498
- if (!nomeVar)
499
- return;
500
- if (!this.variaveis.has(nomeVar)) {
501
- const varLabel = `var_${nomeVar}`;
502
- this.bss += ` ${varLabel}: .space 256\n`;
503
- this.variaveis.set(nomeVar, varLabel);
504
- }
505
- this.text += `
506
- li a0, 0 # fd stdin
507
- la a1, ${this.variaveis.get(nomeVar)}
508
- li a2, 256
509
- li a7, 63 # sys_read
510
- ecall`;
511
- }
512
- traduzirDeclaracaoPara(declaracao) {
513
- const labelInicio = this.gerarLabel();
514
- const labelFim = this.gerarLabel();
515
- if (declaracao.inicializador) {
516
- const tipoInicializador = declaracao.inicializador.constructor.name;
517
- if (this.dicionarioDeclaracoes[tipoInicializador]) {
518
- this.dicionarioDeclaracoes[tipoInicializador](declaracao.inicializador);
519
- }
520
- else if (this.dicionarioConstrutos[tipoInicializador]) {
521
- this.dicionarioConstrutos[tipoInicializador](declaracao.inicializador);
522
- }
523
- }
524
- this.text += `\n${labelInicio}:`;
525
- if (declaracao.condicao) {
526
- const condicao = this.dicionarioConstrutos[declaracao.condicao.constructor.name](declaracao.condicao);
527
- if (condicao !== 'a0') {
528
- this.emitirCarga('a0', condicao);
529
- }
530
- this.text += `\n beqz a0, ${labelFim}`;
531
- }
532
- if (this.dicionarioDeclaracoes[declaracao.corpo.constructor.name]) {
533
- this.dicionarioDeclaracoes[declaracao.corpo.constructor.name](declaracao.corpo);
534
- }
535
- if (declaracao.incrementar) {
536
- if (this.dicionarioConstrutos[declaracao.incrementar.constructor.name]) {
537
- this.dicionarioConstrutos[declaracao.incrementar.constructor.name](declaracao.incrementar);
538
- }
539
- }
540
- this.text += `
541
- j ${labelInicio}
542
- ${labelFim}:`;
543
- }
544
- traduzirDeclaracaoParaCada(declaracao) {
545
- const labelInicio = this.gerarLabel();
546
- const labelFim = this.gerarLabel();
547
- const vetor = declaracao.vetorOuDicionario;
548
- let tamanhoVetor = 0;
549
- if (vetor instanceof construtos_1.Vetor) {
550
- tamanhoVetor = vetor.tamanho || 0;
551
- }
552
- // t0: contador; t1: limite (caller-saved, seguros aqui)
553
- this.text += `
554
- li t0, 0 # contador
555
- li t1, ${tamanhoVetor}
556
- ${labelInicio}:
557
- bge t0, t1, ${labelFim}`;
558
- if (this.dicionarioDeclaracoes[declaracao.corpo.constructor.name]) {
559
- this.dicionarioDeclaracoes[declaracao.corpo.constructor.name](declaracao.corpo);
560
- }
561
- this.text += `
562
- addi t0, t0, 1
563
- j ${labelInicio}
564
- ${labelFim}:`;
565
- }
566
- traduzirDeclaracaoRetorna(declaracao) {
567
- if (declaracao.valor) {
568
- const valor = this.dicionarioConstrutos[declaracao.valor.constructor.name](declaracao.valor);
569
- this.emitirCarga('a0', valor);
570
- }
571
- this.text += `
572
- ld ra, 8(sp)
573
- ld s0, 0(sp)
574
- addi sp, sp, 16
575
- ret`;
576
- }
577
- traduzirDeclaracaoSe(declaracao) {
578
- const labelSenao = this.gerarLabel();
579
- const labelFim = this.gerarLabel();
580
- const condicao = this.dicionarioConstrutos[declaracao.condicao.constructor.name](declaracao.condicao);
581
- if (condicao !== 'a0') {
582
- this.emitirCarga('a0', condicao);
583
- }
584
- this.text += `\n beqz a0, ${labelSenao}`;
585
- if (this.dicionarioDeclaracoes[declaracao.caminhoEntao.constructor.name]) {
586
- this.dicionarioDeclaracoes[declaracao.caminhoEntao.constructor.name](declaracao.caminhoEntao);
587
- }
588
- this.text += `
589
- j ${labelFim}
590
- ${labelSenao}:`;
591
- if (declaracao.caminhoSenao &&
592
- this.dicionarioDeclaracoes[declaracao.caminhoSenao.constructor.name]) {
593
- this.dicionarioDeclaracoes[declaracao.caminhoSenao.constructor.name](declaracao.caminhoSenao);
594
- }
595
- this.text += `\n${labelFim}:`;
596
- }
597
- traduzirDeclaracaoClasse(declaracao) {
598
- this.text += `\n # Classe: ${declaracao.simbolo?.lexema || 'unknown'}`;
599
- }
600
- traduzirDeclaracaoTente(declaracao) {
601
- this.text += `\n # Tente-pegue`;
602
- if (declaracao.caminhoTente && Array.isArray(declaracao.caminhoTente)) {
603
- declaracao.caminhoTente.forEach((decl) => {
604
- if (this.dicionarioDeclaracoes[decl.constructor.name]) {
605
- this.dicionarioDeclaracoes[decl.constructor.name](decl);
606
- }
607
- });
608
- }
609
- }
610
- traduzirDeclaracaoConst(declaracao) {
611
- const nomeVar = declaracao.simbolo?.lexema;
612
- if (!nomeVar)
613
- return;
614
- const valor = this.dicionarioConstrutos[declaracao.inicializador.constructor.name](declaracao.inicializador);
615
- const varLabel = `const_${nomeVar}`;
616
- this.data += ` ${varLabel}: .dword ${valor}\n`;
617
- this.variaveis.set(nomeVar, varLabel);
618
- }
619
- traduzirDeclaracaoVar(declaracao) {
620
- const nomeVar = declaracao.simbolo?.lexema;
621
- if (!nomeVar)
622
- return;
623
- const varLabel = `var_${nomeVar}`;
624
- this.bss += ` ${varLabel}: .space 8\n`;
625
- this.variaveis.set(nomeVar, varLabel);
626
- if (declaracao.inicializador && declaracao.inicializador.valor !== null) {
627
- const tipoInicializador = declaracao.inicializador.constructor.name;
628
- if (declaracao.inicializador instanceof construtos_1.Vetor) {
629
- const labelVetor = this.traduzirConstrutoVetor(declaracao.inicializador);
630
- this.variaveis.set(nomeVar, labelVetor);
631
- }
632
- else if (this.dicionarioConstrutos[tipoInicializador]) {
633
- const valor = this.dicionarioConstrutos[tipoInicializador](declaracao.inicializador);
634
- this.emitirCarga('a0', valor);
635
- this.text += `
636
- la a1, ${varLabel}
637
- sd a0, 0(a1)`;
638
- }
639
- }
640
- }
641
- criarStringLiteral(literal) {
642
- const varLiteral = `Delegua_${this.gerarDigitoAleatorio()}`;
643
- this.data += ` ${varLiteral}: .asciz "${literal.valor}"\n`;
644
- return varLiteral;
645
- }
646
- criarLiteralPontoFlutuante(valor) {
647
- const varLiteral = `Delegua_${this.gerarDigitoAleatorio()}`;
648
- this.data += ` ${varLiteral}: .double ${valor}\n`;
649
- return varLiteral;
650
- }
651
- criarTamanhoNaMemoriaReferenteAVar(nomeStringLiteral) {
652
- return `tam_${nomeStringLiteral}`;
653
- }
654
- traduzirDeclaracaoEscreva(declaracaoEscreva) {
655
- let nomeStringLiteral = '';
656
- let tamanhoString = '';
657
- if (declaracaoEscreva.argumentos[0] instanceof construtos_1.Literal) {
658
- nomeStringLiteral = this.criarStringLiteral(declaracaoEscreva.argumentos[0]);
659
- const stringValue = declaracaoEscreva.argumentos[0].valor;
660
- tamanhoString = String(stringValue.length);
661
- }
662
- // sys_write(fd=1, buf, count): a7=64, a0=fd, a1=buf, a2=count
663
- this.text += `
664
- la a1, ${nomeStringLiteral}
665
- li a2, ${tamanhoString}
666
- li a0, 1 # fd stdout
667
- li a7, 64 # sys_write
668
- ecall`;
669
- }
670
- saidaSistema() {
671
- this.text += `
672
- li a0, 0 # código de saída
673
- li a7, 93 # sys_exit
674
- ecall`;
675
- }
676
- traduzir(declaracoes) {
677
- this.declaracoesDeClasses = declaracoes.filter((declaracao) => declaracao instanceof declaracoes_1.Classe);
678
- for (const declaracao of declaracoes) {
679
- if (this.dicionarioDeclaracoes[declaracao.constructor.name]) {
680
- this.dicionarioDeclaracoes[declaracao.constructor.name](declaracao);
681
- }
682
- }
683
- this.saidaSistema();
684
- return this.bss + '\n' + this.data + '\n' + this.text;
685
- }
686
- }
687
- exports.TradutorAssemblyRISCV = TradutorAssemblyRISCV;
688
- //# sourceMappingURL=tradutor-assembly-risc-v.js.map