Skip to content

Commit 012c55e

Browse files
committed
Fix #1: Include annotations as metadata
1 parent c7cfbf7 commit 012c55e

File tree

2 files changed

+31
-19
lines changed

2 files changed

+31
-19
lines changed

ChangeLog.md

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,9 @@ XP Compiler ChangeLog
33

44
## ?.?.? / ????-??-??
55

6+
* Optimized runtime performance by including annotations as
7+
metadata inside code, see issue #1.
8+
(@thekid)
69
* Fixed annotation parsing - @thekid
710
* Made `xp help compile` display something useful - @thekid
811
* Fixed compatibility with XP7 console streaming - @thekid

src/main/php/lang/ast/Emitter.class.php

Lines changed: 28 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,11 @@
66
use io\streams\StringWriter;
77

88
abstract class Emitter {
9+
const PROPERTY = 0;
10+
const METHOD = 1;
11+
912
protected $out;
13+
protected $meta= [];
1014

1115
/**
1216
* Selects the correct emitter for a given runtime version
@@ -98,21 +102,6 @@ protected function arguments($list) {
98102
}
99103
}
100104

101-
protected function annotations($list) {
102-
$s= sizeof($list) - 1;
103-
$this->out->write('#[');
104-
foreach ($list as $i => $annotation) {
105-
$this->out->write('@'.$annotation[0]);
106-
if (isset($annotation[1])) {
107-
$this->out->write('(');
108-
$this->arguments($annotation[1]);
109-
$this->out->write(')');
110-
}
111-
if ($i < $s) $this->out->write(', ');
112-
}
113-
$this->out->write("]\n");
114-
}
115-
116105
protected function emitStart($node) {
117106
$this->out->write('<?php ');
118107
}
@@ -195,6 +184,7 @@ protected function emitClosure($node) {
195184
}
196185

197186
protected function emitClass($node) {
187+
array_unshift($this->meta, []);
198188
$this->out->write(implode(' ', $node->value[1]).' class '.$node->value[0]);
199189
$node->value[2] && $this->out->write(' extends '.$node->value[2]);
200190
$node->value[3] && $this->out->write(' implements '.implode(', ', $node->value[3]));
@@ -204,6 +194,27 @@ protected function emitClass($node) {
204194
$this->out->write("\n");
205195
}
206196
$this->out->write('}');
197+
198+
// Cache annotations
199+
$this->out->write('\xp::$meta[\''.$node->value[0].'\']= [');
200+
foreach (array_shift($this->meta) as $type => $lookup) {
201+
$this->out->write($type.' => [');
202+
foreach ($lookup as $key => $annotations) {
203+
$this->out->write("'".$key."' => [DETAIL_ANNOTATIONS => [");
204+
foreach ($annotations as $annotation) {
205+
$this->out->write("'".$annotation[0]."' => ");
206+
if (isset($annotation[1])) {
207+
$this->emit($annotation[1]);
208+
$this->out->write('null');
209+
} else {
210+
$this->out->write('null,');
211+
}
212+
}
213+
$this->out->write(']],');
214+
}
215+
$this->out->write('],');
216+
}
217+
$this->out->write('];');
207218
}
208219

209220
protected function emitInterface($node) {
@@ -238,8 +249,7 @@ protected function emitProperty($node) {
238249
$this->out->write("\n/** @var ".$node->value[3]." */\n");
239250
}
240251
if (isset($node->value[4])) {
241-
$this->out->write("\n");
242-
$this->annotations($node->value[4]);
252+
$this->meta[0][self::PROPERTY][$node->value[0]]= $node->value[4];
243253
}
244254
$this->out->write(implode(' ', $node->value[1]).' $'.$node->value[0]);
245255
if (isset($node->value[2])) {
@@ -259,8 +269,7 @@ protected function emitMethod($node) {
259269
}
260270
$this->out->write($declare);
261271
if (isset($node->value[6])) {
262-
$this->out->write("\n");
263-
$this->annotations($node->value[6]);
272+
$this->meta[0][self::METHOD][$node->value[0]]= $node->value[6];
264273
}
265274
$this->out->write(implode(' ', $node->value[1]).' function '.$node->value[0].'(');
266275
$this->params($node->value[2]);

0 commit comments

Comments
 (0)