1 : /*
2 : +----------------------------------------------------------------------+
3 : | Zend Engine |
4 : +----------------------------------------------------------------------+
5 : | Copyright (c) 1998-2009 Zend Technologies Ltd. (http://www.zend.com) |
6 : +----------------------------------------------------------------------+
7 : | This source file is subject to version 2.00 of the Zend license, |
8 : | that is bundled with this package in the file LICENSE, and is |
9 : | available through the world-wide-web at the following url: |
10 : | http://www.zend.com/license/2_00.txt. |
11 : | If you did not receive a copy of the Zend license and are unable to |
12 : | obtain it through the world-wide-web, please send a note to |
13 : | license@zend.com so we can mail you a copy immediately. |
14 : +----------------------------------------------------------------------+
15 : | Authors: Andi Gutmans <andi@zend.com> |
16 : | Zeev Suraski <zeev@zend.com> |
17 : +----------------------------------------------------------------------+
18 : */
19 :
20 : /* $Id: zend_highlight.c 279940 2009-05-05 01:35:13Z mattwil $ */
21 :
22 : #include "zend.h"
23 : #include <zend_language_parser.h>
24 : #include "zend_compile.h"
25 : #include "zend_highlight.h"
26 : #include "zend_ptr_stack.h"
27 : #include "zend_globals.h"
28 : #include "zend_operators.h"
29 :
30 : ZEND_API void zend_html_putc(char c) /* {{{ */
31 4108 : {
32 4108 : switch (c) {
33 : case '\n':
34 106 : ZEND_PUTS("<br />");
35 106 : break;
36 : case '<':
37 49 : ZEND_PUTS("<");
38 49 : break;
39 : case '>':
40 19 : ZEND_PUTS(">");
41 19 : break;
42 : case '&':
43 4 : ZEND_PUTS("&");
44 4 : break;
45 : case ' ':
46 284 : ZEND_PUTS(" ");
47 284 : break;
48 : case '\t':
49 17 : ZEND_PUTS(" ");
50 17 : break;
51 : default:
52 3629 : ZEND_PUTC(c);
53 : break;
54 : }
55 4108 : }
56 : /* }}} */
57 :
58 : ZEND_API void zend_html_puts(const char *s, uint len TSRMLS_DC) /* {{{ */
59 816 : {
60 816 : const char *ptr=s, *end=s+len;
61 :
62 5720 : while (ptr<end) {
63 4088 : if (*ptr==' ') {
64 : do {
65 284 : zend_html_putc(*ptr);
66 284 : } while ((++ptr < end) && (*ptr==' '));
67 : } else {
68 3824 : zend_html_putc(*ptr++);
69 : }
70 : }
71 816 : }
72 : /* }}} */
73 :
74 : ZEND_API void zend_highlight(zend_syntax_highlighter_ini *syntax_highlighter_ini TSRMLS_DC) /* {{{ */
75 32 : {
76 : zval token;
77 : int token_type;
78 32 : char *last_color = syntax_highlighter_ini->highlight_html;
79 : char *next_color;
80 :
81 32 : CG(literal_type) = IS_STRING;
82 32 : zend_printf("<code>");
83 32 : zend_printf("<span style=\"color: %s\">\n", last_color);
84 : /* highlight stuff coming back from zendlex() */
85 32 : Z_TYPE(token) = 0;
86 669 : while ((token_type=lex_scan(&token TSRMLS_CC))) {
87 605 : switch (token_type) {
88 : case T_INLINE_HTML:
89 11 : next_color = syntax_highlighter_ini->highlight_html;
90 11 : break;
91 : case T_COMMENT:
92 : case T_DOC_COMMENT:
93 11 : next_color = syntax_highlighter_ini->highlight_comment;
94 11 : break;
95 : case T_OPEN_TAG:
96 : case T_OPEN_TAG_WITH_ECHO:
97 30 : next_color = syntax_highlighter_ini->highlight_default;
98 30 : break;
99 : case T_CLOSE_TAG:
100 14 : next_color = syntax_highlighter_ini->highlight_default;
101 14 : break;
102 : case '"':
103 : case T_ENCAPSED_AND_WHITESPACE:
104 : case T_CONSTANT_ENCAPSED_STRING:
105 36 : next_color = syntax_highlighter_ini->highlight_string;
106 36 : break;
107 : case T_WHITESPACE:
108 191 : zend_html_puts(LANG_SCNG(yy_text), LANG_SCNG(yy_leng) TSRMLS_CC); /* no color needed */
109 191 : Z_TYPE(token) = 0;
110 191 : continue;
111 : break;
112 : default:
113 312 : if (Z_TYPE(token) == 0) {
114 234 : next_color = syntax_highlighter_ini->highlight_keyword;
115 : } else {
116 78 : next_color = syntax_highlighter_ini->highlight_default;
117 : }
118 : break;
119 : }
120 :
121 414 : if (last_color != next_color) {
122 293 : if (last_color != syntax_highlighter_ini->highlight_html) {
123 263 : zend_printf("</span>");
124 : }
125 293 : last_color = next_color;
126 293 : if (last_color != syntax_highlighter_ini->highlight_html) {
127 290 : zend_printf("<span style=\"color: %s\">", last_color);
128 : }
129 : }
130 :
131 414 : zend_html_puts(LANG_SCNG(yy_text), LANG_SCNG(yy_leng) TSRMLS_CC);
132 :
133 575 : if (Z_TYPE(token) == IS_STRING ||
134 : Z_TYPE(token) == IS_UNICODE) {
135 161 : switch (token_type) {
136 : case T_OPEN_TAG:
137 : case T_OPEN_TAG_WITH_ECHO:
138 : case T_CLOSE_TAG:
139 : case T_WHITESPACE:
140 : case T_COMMENT:
141 : case T_DOC_COMMENT:
142 44 : break;
143 : default:
144 117 : efree(Z_UNIVAL(token).v);
145 : break;
146 : }
147 253 : } else if (token_type == T_END_HEREDOC) {
148 3 : efree(Z_UNIVAL(token).v);
149 : }
150 414 : Z_TYPE(token) = 0;
151 : }
152 :
153 32 : if (last_color != syntax_highlighter_ini->highlight_html) {
154 27 : zend_printf("</span>\n");
155 : }
156 32 : zend_printf("</span>\n");
157 32 : zend_printf("</code>");
158 32 : }
159 : /* }}} */
160 :
161 : ZEND_API void zend_strip(TSRMLS_D) /* {{{ */
162 7 : {
163 : zval token;
164 : int token_type;
165 7 : int prev_space = 0;
166 :
167 7 : CG(literal_type) = IS_STRING;
168 7 : Z_TYPE(token) = 0;
169 195 : while ((token_type=lex_scan(&token TSRMLS_CC))) {
170 181 : switch (token_type) {
171 : case T_WHITESPACE:
172 73 : if (!prev_space) {
173 59 : zend_write(" ", sizeof(" ") - 1);
174 59 : prev_space = 1;
175 : }
176 : /* lack of break; is intentional */
177 : case T_COMMENT:
178 : case T_DOC_COMMENT:
179 97 : Z_TYPE(token) = 0;
180 97 : continue;
181 :
182 : case T_END_HEREDOC:
183 0 : zend_write(LANG_SCNG(yy_text), LANG_SCNG(yy_leng));
184 0 : efree(Z_STRVAL(token));
185 : /* read the following character, either newline or ; */
186 0 : if (lex_scan(&token TSRMLS_CC) != T_WHITESPACE) {
187 0 : zend_write(LANG_SCNG(yy_text), LANG_SCNG(yy_leng));
188 : }
189 0 : zend_write("\n", sizeof("\n") - 1);
190 0 : prev_space = 1;
191 0 : Z_TYPE(token) = 0;
192 0 : continue;
193 :
194 : default:
195 84 : zend_write(LANG_SCNG(yy_text), LANG_SCNG(yy_leng));
196 : break;
197 : }
198 :
199 84 : if (Z_TYPE(token) == IS_STRING ||
200 : Z_TYPE(token) == IS_UNICODE) {
201 32 : switch (token_type) {
202 : case T_OPEN_TAG:
203 : case T_OPEN_TAG_WITH_ECHO:
204 : case T_CLOSE_TAG:
205 : case T_WHITESPACE:
206 : case T_COMMENT:
207 : case T_DOC_COMMENT:
208 12 : break;
209 :
210 : default:
211 20 : efree(Z_UNIVAL(token).v);
212 : break;
213 : }
214 : }
215 84 : prev_space = Z_TYPE(token) = 0;
216 : }
217 7 : }
218 : /* }}} */
219 :
220 : /*
221 : * Local variables:
222 : * tab-width: 4
223 : * c-basic-offset: 4
224 : * indent-tabs-mode: t
225 : * End:
226 : */
|