2011-08-04 14 views
6

Me pregunto si es posible que un Recurso PHP válido tenga un ID de 0. Estoy obteniendo recursos de conexión a la base de datos y hasta ahora todos han sido enteros positivos distintos de cero. Solo curiosidad por saber cuál es el rango de ID potenciales para los recursos.¿Puede PHP devolver un recurso con ID # 0?

+0

Pregunta realmente genial. – barfoon

Respuesta

4

La identificación del recurso puede estar en el rango de int. Busque "resource" o "ZEND_FETCH_RESOURCE" en el directorio del código fuente de PHP a través de la terminal. A continuación, verá la función:
(archivo ./Zend/zend_list.c, línea 110)

ZEND_API void *zend_fetch_resource(zval **passed_id TSRMLS_DC, int default_id, 
char *resource_type_name, int *found_resource_type, int num_resource_types, ...) 

Dentro de la función, verá que es passed_id Identificación del recurso y es de tipo int.
Normalmente, las bibliotecas pasar un identificador predeterminado de -1, por ejemplo en el archivo ./ext/mysql/php_mysql.c, línea 1060.

En general se puede asumir que todas las bibliotecas pasarán un verdadero/existe Identificación del recurso con valor mayor que 0, pero eso es no es una regla que toda biblioteca debe seguir: es posible pasar un identificador de recurso negativo o 0.

3

No parece ... no pude encontrar exactamente por qué, pero aquí es lo que he tratado (tal vez alguien puede arrojar algo más de luz sobre este comportamiento para el motor de Zend)

1.- En C, que escribió un programa muy tonta que genera un descriptor de archivo # 0 (esto no es análogo a un recurso en php, pero he intentado esto con recursos de archivos, así que puede relacionarse de alguna manera los dos idiomas)

#include <stdio.h> 
#include <string.h> 
#include <sys/types.h> 
#include <sys/stat.h> 
#include <fcntl.h> 


int 
main(int argc, char *argv[]) 
{ 
    int a; 
    char buff[8]; 
    close(0); 
    close(1); 
    close(2); 
    a = open("./output", O_CREAT | O_TRUNC | O_WRONLY); 
    sprintf(buff, "%d\n", a); 
    write(a, buff, strlen(buff)); 
    close(a); 
} 

Este código cerrará los descriptores de archivos 0, 1, 2. abrirá un nuevo archivo y guardará el descriptor, que resulta en:

$ salida gato

$

ahora, en php:

<?php 
fclose(STDIN); 
fclose(STDOUT); 
fclose(STDERR); 

$asd = fopen('./outputphp', 'w'); 
fwrite($asd, print_r($asd, true)); 
fclose($asd); 

esta es la salida:

$ cat outputphp

Resource id # 5

$

así que incluso al cerrar stdin, stdout y stderr, php no reutilizará los identificadores de recursos. aún más, stdin id # 1, stdout es # 2 y stderr es # 3 cuando en realidad stdin tiene el descriptor de archivo 0, stdout tiene 1 y stderr tiene 2. también, hay otra identificación # 4 ya asignada.

entonces yo diría que php se reserva el id # 0 o no lo usará en absoluto.

greping a través del código del motor zend, encontré que realmente el recurso # 0 se usa en todo el código que inicializa el motor Zend en sapi (cgi, cli, modules, etc.) cuando ZTS (seguridad de subprocesos está habilitado). como:

tsrm_startup(1, 1, 0, NULL); 
tsrm_ls = ts_resource(0); 

al limpiar el motor Zend, que atravesará la tabla de recursos a partir de la ID # 0. No se puede (al menos no pude) obtener un recurso # 0 con o sin la seguridad de subprocesos activada, por lo que # 0 parece estar reservado para ambos casos, pero solo se usa cuando ts está habilitado.

EDITAR: para resumir;) parece que no puede tener una identificación de recursos inferior a 1, siendo 1, 2, 3 abierto por defecto (no estoy seguro del # 4, pero es posible que se abra cualquier recurso nuevo comenzará en # 4 o # 5)

Cuestiones relacionadas