/** * Emit a log message. This function is the variable argument list equivalent * to vlc_Log(). */ void vlc_vaLog (vlc_object_t *obj, int type, const char *module, const char *file, unsigned line, const char *func, const char *format, va_list args) { if (obj != NULL && obj->obj.flags & OBJECT_FLAGS_QUIET) return; /* Get basename from the module filename */ char *p = strrchr(module, '/'); if (p != NULL) module = p + 1; p = strchr(module, '.'); size_t modlen = (p != NULL) ? (p - module) : 0; char modulebuf[modlen + 1]; if (p != NULL) { memcpy(modulebuf, module, modlen); modulebuf[modlen] = '\0'; module = modulebuf; } /* Fill message information fields */ vlc_log_t msg; msg.i_object_id = (uintptr_t)obj; msg.psz_object_type = (obj != NULL) ? obj->obj.object_type : "generic"; msg.psz_module = module; msg.psz_header = NULL; msg.file = file; msg.line = line; msg.func = func; msg.tid = vlc_thread_id(); for (vlc_object_t *o = obj; o != NULL; o = o->obj.parent) if (o->obj.header != NULL) { msg.psz_header = o->obj.header; break; } #ifdef _WIN32 va_list ap; va_copy (ap, args); Win32DebugOutputMsg (NULL, type, &msg, format, ap); va_end (ap); #endif /* Pass message to the callback */ if (obj != NULL) vlc_vaLogCallback(obj->obj.libvlc, type, &msg, format, args); }
/** * Emit a log message. This function is the variable argument list equivalent * to vlc_Log(). */ void vlc_vaLog (vlc_object_t *obj, int type, const char *module, const char *format, va_list args) { if (obj != NULL && obj->i_flags & OBJECT_FLAGS_QUIET) return; /* Get basename from the module filename */ char *p = strrchr(module, '/'); if (p != NULL) module = p; p = strchr(module, '.'); size_t modlen = (p != NULL) ? (p - module) : 1; char modulebuf[modlen + 1]; if (p != NULL) { memcpy(modulebuf, module, modlen); modulebuf[modlen] = '\0'; module = modulebuf; } /* Fill message information fields */ vlc_log_t msg; msg.i_object_id = (uintptr_t)obj; msg.psz_object_type = (obj != NULL) ? obj->psz_object_type : "generic"; msg.psz_module = module; msg.psz_header = NULL; for (vlc_object_t *o = obj; o != NULL; o = o->p_parent) if (o->psz_header != NULL) { msg.psz_header = o->psz_header; break; } /* Pass message to the callback */ libvlc_priv_t *priv = obj ? libvlc_priv (obj->p_libvlc) : NULL; #ifdef _WIN32 va_list ap; va_copy (ap, args); Win32DebugOutputMsg (priv ? &priv->log.verbose : NULL, type, &msg, format, ap); va_end (ap); #endif if (priv) { vlc_rwlock_rdlock (&priv->log.lock); priv->log.cb (priv->log.opaque, type, &msg, format, args); vlc_rwlock_unlock (&priv->log.lock); } }
/** * Emit a log message. This function is the variable argument list equivalent * to vlc_Log(). */ void vlc_vaLog (vlc_object_t *obj, int type, const char *module, const char *format, va_list args) { if (obj != NULL && obj->i_flags & OBJECT_FLAGS_QUIET) return; /* Get basename from the module filename */ char *p = strrchr(module, '/'); if (p != NULL) module = p; p = strchr(module, '.'); size_t modlen = (p != NULL) ? (p - module) : 1; char modulebuf[modlen]; if (p != NULL) { memcpy(modulebuf, module, modlen); modulebuf[modlen] = '\0'; module = modulebuf; } /* C locale to get error messages in English in the logs */ locale_t c = newlocale (LC_MESSAGES_MASK, "C", (locale_t)0); locale_t locale = uselocale (c); #ifndef __GLIBC__ /* Expand %m to strerror(errno) - only once */ char buf[strlen(format) + 2001], *ptr; strcpy (buf, format); ptr = (char*)buf; format = (const char*) buf; for( ;; ) { ptr = strchr( ptr, '%' ); if( ptr == NULL ) break; if( ptr[1] == 'm' ) { char errbuf[2001]; size_t errlen; #ifndef _WIN32 strerror_r( errno, errbuf, 1001 ); #else int sockerr = WSAGetLastError( ); if( sockerr ) { strncpy( errbuf, net_strerror( sockerr ), 1001 ); WSASetLastError( sockerr ); } if ((sockerr == 0) || (strcmp ("Unknown network stack error", errbuf) == 0)) strncpy( errbuf, strerror( errno ), 1001 ); #endif errbuf[1000] = 0; /* Escape '%' from the error string */ for( char *percent = strchr( errbuf, '%' ); percent != NULL; percent = strchr( percent + 2, '%' ) ) { memmove( percent + 1, percent, strlen( percent ) + 1 ); } errlen = strlen( errbuf ); memmove( ptr + errlen, ptr + 2, strlen( ptr + 2 ) + 1 ); memcpy( ptr, errbuf, errlen ); break; /* Only once, so we don't overflow */ } /* Looks for conversion specifier... */ do ptr++; while( *ptr && ( strchr( "diouxXeEfFgGaAcspn%", *ptr ) == NULL ) ); if( *ptr ) ptr++; /* ...and skip it */ } #endif /* Fill message information fields */ vlc_log_t msg; msg.i_object_id = (uintptr_t)obj; msg.psz_object_type = (obj != NULL) ? obj->psz_object_type : "generic"; msg.psz_module = module; msg.psz_header = NULL; for (vlc_object_t *o = obj; o != NULL; o = o->p_parent) if (o->psz_header != NULL) { msg.psz_header = o->psz_header; break; } /* Pass message to the callback */ libvlc_priv_t *priv = obj ? libvlc_priv (obj->p_libvlc) : NULL; #ifdef _WIN32 va_list ap; va_copy (ap, args); Win32DebugOutputMsg (priv ? &priv->log.verbose : NULL, type, &msg, format, ap); va_end (ap); #endif if (priv) { vlc_rwlock_rdlock (&priv->log.lock); priv->log.cb (priv->log.opaque, type, &msg, format, args); vlc_rwlock_unlock (&priv->log.lock); } uselocale (locale); freelocale (c); }