/* {{{ mysqlnd_res_meta::func_enter */ static zend_bool MYSQLND_METHOD(mysqlnd_debug, func_enter)(MYSQLND_DEBUG * self, unsigned int line, const char * const file, const char * const func_name, unsigned int func_name_len) { if ((self->flags & MYSQLND_DEBUG_DUMP_TRACE) == 0 || self->file_name == NULL) { return FALSE; } if (zend_stack_count(&self->call_stack) >= self->nest_level_limit) { return FALSE; } if ((self->flags & MYSQLND_DEBUG_TRACE_MEMORY_CALLS) == 0 && self->skip_functions) { const char ** p = self->skip_functions; while (*p) { if (*p == func_name) { zend_stack_push(&self->call_stack, "", sizeof("")); return FALSE; } p++; } } zend_stack_push(&self->call_stack, func_name, func_name_len + 1); if (zend_hash_num_elements(&self->not_filtered_functions) && 0 == zend_hash_exists(&self->not_filtered_functions, func_name, strlen(func_name) + 1)) { return FALSE; } self->m->log_va(self, line, file, zend_stack_count(&self->call_stack) - 1, NULL, ">%s", func_name); return TRUE; }
/* {{{ mysqlnd_res_meta::func_leave */ static enum_func_status MYSQLND_METHOD(mysqlnd_debug, func_leave)(MYSQLND_DEBUG * self, unsigned int line, const char * const file) { char *func_name; #ifdef MYSQLND_THREADED MYSQLND_ZTS(self); #endif if ((self->flags & MYSQLND_DEBUG_DUMP_TRACE) == 0 || self->file_name == NULL) { return PASS; } #ifdef MYSQLND_THREADED if (MYSQLND_G(thread_id) != tsrm_thread_id()) { return PASS; /* don't trace background threads */ } #endif if (zend_stack_count(&self->call_stack) >= self->nest_level_limit) { return PASS; } zend_stack_top(&self->call_stack, (void **)&func_name); if (func_name[0] == '\0') { ; /* don't log that function */ } else if (!zend_hash_num_elements(&self->not_filtered_functions) || 1 == zend_hash_exists(&self->not_filtered_functions, func_name, strlen(func_name) + 1)) { self->m->log_va(self, line, file, zend_stack_count(&self->call_stack) - 1, NULL, "<%s", func_name); } return zend_stack_del_top(&self->call_stack) == SUCCESS? PASS:FAIL; }
/* {{{ mysqlnd_res_meta::func_enter */ static zend_bool MYSQLND_METHOD(mysqlnd_debug, func_enter)(MYSQLND_DEBUG * self, unsigned int line, const char * const file, char * func_name, unsigned int func_name_len) { #ifdef MYSQLND_THREADED MYSQLND_ZTS(self); #endif if ((self->flags & MYSQLND_DEBUG_DUMP_TRACE) == 0 || self->file_name == NULL) { return FALSE; } #ifdef MYSQLND_THREADED if (MYSQLND_G(thread_id) != tsrm_thread_id()) { return FALSE; /* don't trace background threads */ } #endif if (zend_stack_count(&self->call_stack) >= self->nest_level_limit) { return FALSE; } if ((self->flags & MYSQLND_DEBUG_TRACE_MEMORY_CALLS) == 0 && (func_name == mysqlnd_emalloc_name || func_name == mysqlnd_pemalloc_name || func_name == mysqlnd_ecalloc_name || func_name == mysqlnd_pecalloc_name || func_name == mysqlnd_erealloc_name || func_name == mysqlnd_perealloc_name || func_name == mysqlnd_efree_name || func_name == mysqlnd_pefree_name || func_name == mysqlnd_malloc_name || func_name == mysqlnd_calloc_name || func_name == mysqlnd_realloc_name || func_name == mysqlnd_free_name || func_name == mysqlnd_palloc_zval_ptr_dtor_name || func_name == mysqlnd_palloc_get_zval_name || func_name == mysqlnd_read_header_name || func_name == mysqlnd_read_body_name)) { zend_stack_push(&self->call_stack, "", sizeof("")); return FALSE; } zend_stack_push(&self->call_stack, func_name, func_name_len + 1); if (zend_hash_num_elements(&self->not_filtered_functions) && 0 == zend_hash_exists(&self->not_filtered_functions, func_name, strlen(func_name) + 1)) { return FALSE; } self->m->log_va(self, line, file, zend_stack_count(&self->call_stack) - 1, NULL, ">%s", func_name); return TRUE; }
/* {{{ int php_output_get_level(TSRMLS_D) * Get output buffering level, ie. how many output handlers the stack contains */ PHPAPI int php_output_get_level(TSRMLS_D) { return OG(active) ? zend_stack_count(&OG(handlers)) : 0; }
/* {{{ mysqlnd_debug::log_va */ static enum_func_status MYSQLND_METHOD(mysqlnd_debug, log_va)(MYSQLND_DEBUG *self, unsigned int line, const char * const file, unsigned int level, const char * type, const char *format, ...) { char pipe_buffer[512]; int i; enum_func_status ret; char * message_line, *buffer; unsigned int message_line_len; va_list args; unsigned int flags = self->flags; char pid_buffer[10], time_buffer[30], file_buffer[200], line_buffer[6], level_buffer[7]; MYSQLND_ZTS(self); if (!self->stream) { if (FAIL == self->m->open(self, FALSE)) { return FAIL; } } if (level == -1) { level = zend_stack_count(&self->call_stack); } i = MIN(level, sizeof(pipe_buffer) / 2 - 1); pipe_buffer[i*2] = '\0'; for (;i > 0;i--) { pipe_buffer[i*2 - 1] = ' '; pipe_buffer[i*2 - 2] = '|'; } if (flags & MYSQLND_DEBUG_DUMP_PID) { snprintf(pid_buffer, sizeof(pid_buffer) - 1, "%5u: ", self->pid); pid_buffer[sizeof(pid_buffer) - 1 ] = '\0'; } if (flags & MYSQLND_DEBUG_DUMP_TIME) { /* The following from FF's DBUG library, which is in the public domain */ #if defined(PHP_WIN32) /* FIXME This doesn't give microseconds as in Unix case, and the resolution is in system ticks, 10 ms intervals. See my_getsystime.c for high res */ SYSTEMTIME loc_t; GetLocalTime(&loc_t); snprintf(time_buffer, sizeof(time_buffer) - 1, /* "%04d-%02d-%02d " */ "%02d:%02d:%02d.%06d ", /*tm_p->tm_year + 1900, tm_p->tm_mon + 1, tm_p->tm_mday,*/ loc_t.wHour, loc_t.wMinute, loc_t.wSecond, loc_t.wMilliseconds); time_buffer[sizeof(time_buffer) - 1 ] = '\0'; #else struct timeval tv; struct tm *tm_p; if (gettimeofday(&tv, NULL) != -1) { if ((tm_p= localtime((const time_t *)&tv.tv_sec))) { snprintf(time_buffer, sizeof(time_buffer) - 1, /* "%04d-%02d-%02d " */ "%02d:%02d:%02d.%06d ", /*tm_p->tm_year + 1900, tm_p->tm_mon + 1, tm_p->tm_mday,*/ tm_p->tm_hour, tm_p->tm_min, tm_p->tm_sec, (int) (tv.tv_usec)); time_buffer[sizeof(time_buffer) - 1 ] = '\0'; } } #endif } if (flags & MYSQLND_DEBUG_DUMP_FILE) { snprintf(file_buffer, sizeof(file_buffer) - 1, "%14s: ", file); file_buffer[sizeof(file_buffer) - 1 ] = '\0'; } if (flags & MYSQLND_DEBUG_DUMP_LINE) { snprintf(line_buffer, sizeof(line_buffer) - 1, "%5u: ", line); line_buffer[sizeof(line_buffer) - 1 ] = '\0'; } if (flags & MYSQLND_DEBUG_DUMP_LEVEL) { snprintf(level_buffer, sizeof(level_buffer) - 1, "%4u: ", level); level_buffer[sizeof(level_buffer) - 1 ] = '\0'; } va_start(args, format); vspprintf(&buffer, 0, format, args); va_end(args); message_line_len = spprintf(&message_line, 0, "%s%s%s%s%s%s%s%s\n", flags & MYSQLND_DEBUG_DUMP_PID? pid_buffer:"", flags & MYSQLND_DEBUG_DUMP_TIME? time_buffer:"", flags & MYSQLND_DEBUG_DUMP_FILE? file_buffer:"", flags & MYSQLND_DEBUG_DUMP_LINE? line_buffer:"", flags & MYSQLND_DEBUG_DUMP_LEVEL? level_buffer:"", pipe_buffer, type? type:"", buffer); efree(buffer); ret = php_stream_write(self->stream, message_line, message_line_len)? PASS:FAIL; efree(message_line); if (flags & MYSQLND_DEBUG_FLUSH) { self->m->close(self); self->m->open(self, TRUE); } return ret; }