[PHP-dev 1354] Re: echo,printの実装

Seiji Masugata s.masugata @ digicom.dnp.co.jp
2006年 12月 14日 (木) 19:56:16 JST


こんばんわ、桝形です。

> 浅野です。
> 
> echo,printの処理はどこで行っているのでしょうか?

意外と深い位置にあるのですが、

/(php-src)/Zend/zend_compile.c
void zend_do_echo(znode *arg TSRMLS_DC)
void zend_do_print(znode *result, znode *arg TSRMLS_DC)

/(php-src)/Zend/zend_execute.c
			case ZEND_ECHO:
				zend_print_variable(get_zval_ptr(&EX(opline)->op1, EX(Ts), &EG(free_op1), BP_VAR_R));
			case ZEND_PRINT:
				zend_print_variable(get_zval_ptr(&EX(opline)->op1, EX(Ts), &EG(free_op1), BP_VAR_R));

/(php-src)/Zend/zend_variables.c
ZEND_API int zend_print_variable(zval *var) 
{
	return zend_print_zval(var, 0);
}

/(php-src)/Zend/zend.c
ZEND_API int zend_print_zval(zval *expr, int indent)
{
	return zend_print_zval_ex(zend_write, expr, indent);
}

ZEND_API int zend_print_zval_ex(zend_write_func_t write_func, zval *expr, int indent)


4.4.4ですが、このような流れになるのかと。。。
5.2.0は構造が変わってるので、まだ追え切れていないのですが、

/(php-src)/Zend/zend_compile.c
void zend_do_echo(znode *arg TSRMLS_DC)
void zend_do_print(znode *result, znode *arg TSRMLS_DC)

/(php-src)/Zend/zend_vm_opcodes.h
#define ZEND_ECHO                     40
#define ZEND_PRINT                    41

/(php-src)/Zend/zend_vm.h
ZEND_VM_HANDLER(40, ZEND_ECHO, CONST|TMP|VAR|CV, ANY)
ZEND_VM_HANDLER(41, ZEND_PRINT, CONST|TMP|VAR|CV, ANY)


/(php-src)/Zend/zend_variables.c
ZEND_API int zend_print_variable(zval *var) 
{
	return zend_print_zval(var, 0);
}

/(php-src)/Zend/zend.c
ZEND_API int zend_print_zval(zval *expr, int indent)
{
	return zend_print_zval_ex(zend_write, expr, indent);
}

恐らく、このような流れになるのかと。。。中途半端でスミマセン。


> printfなどの標準関数はext/standard/以下に在るようですが。
> マニュアルには「正確には関数ではなく言語構造」とありますがどういうことでしょう?

すみません。自分もヨク分かっていないのですが、PHPの言語としてみた時には
echoは関数では無い(出力命令であるので関数としての使い方は出来ない)、と
いう事が言いたいのかな、と個人的には思ってました。

php -r 'echo ( echo ( "1" ) );'

http://jp2.php.net/echo
-----------------------------------------------------------------------
echo() は実際には関数ではありません (言語構造です) 。

このため、使用する際に括弧は必要ありません。 (いくつかの他の言語構造と
異なり) echo()  は関数のように動作しません。

そのため、 常に関数のコンテキスト中で使用することはできません。 
加えて、複数のパラメータを指定して echo()  をコールしたい場合、括弧の
中にパラメータを記述するべきではありません。
-----------------------------------------------------------------------

言語構造 == (基本的な構文 + 型 + 変数 + 定数 + 式 + 演算子 + 制御構造)

みたいな事なんじゃないのかと。。。

-- 
Seiji Masugata <s.masugata @ digicom.dnp.co.jp>



PHP-dev メーリングリストの案内