2010-04-15 9 views
13

tengo un montón de Console.WriteLines en mi código que puedo observar en tiempo de ejecución. Me comunico con una biblioteca nativa que también escribí.problemas con Console.SetOut en modo de lanzamiento?

Me gustaría incluir algunos printf en la biblioteca nativa y observarlos también. Sin embargo, no los veo en tiempo de ejecución.

He creado una complicada aplicación hello world para demostrar mi problema. Cuando se ejecuta la aplicación, puedo depurar en la biblioteca nativa y ver que se llama el mundo hello. Sin embargo, la salida nunca cae en el texto. Tenga en cuenta que si el mismo código se ejecuta como una aplicación de consola, todo funciona bien.

C#:

[DllImport("native.dll")] 
    static extern void Test(); 

    StreamWriter writer; 

    public Form1() 
    { 
     InitializeComponent(); 

     writer = new StreamWriter(@"c:\output.txt"); 
     writer.AutoFlush = true; 
     System.Console.SetOut(writer); 
    } 

    private void button1_Click(object sender, EventArgs e) 
    { 
     Test(); 
    } 

y la parte nativa:

__declspec(dllexport) void Test() 
{ 
    printf("Hello World"); 
} 

Actualización: hamishmcn continuación comenzaron a hablar de depuración/versiones de lanzamiento. Eliminé la llamada nativa en el método button1_click anterior y simplemente la reemplacé por una llamada estándar Console.WriteLine .net. Cuando compilé y ejecuté esto en modo de depuración, los mensajes fueron redirigidos al archivo de salida. Cuando cambié al modo de liberación, sin embargo, las llamadas no fueron redirigidas. La redirección de consola solo parece funcionar en modo de depuración. ¿Cómo puedo evitar esto?

+0

Sin respuesta, pero esta publicación http://stackoverflow.com/questions/2570001/allow-native-dll-to-output-stdout-stderr-in-c-console-application sugiere que debería funcionar bien. Hmm. Parece que stdout está redireccionando a otro lugar; ya sea eso o está siendo amortiguado. –

+1

¿Cómo se está ejecutando/conectando a la biblioteca nativa? – chilltemp

+0

Me he adjuntado al proceso a través de vs.net y también dejé que se ejecute en la consola, y no veo nada de la extensión nativa. También probé DbgView, que tampoco produce nada nativo, solo mis mensajes .net. –

Respuesta

1

la redirección de consola sólo funciona en modo de depuración.

1

Actualmente no tengo ningún proyecto en el que pueda intentarlo, pero definitivamente sospecho que hay memoria intermedia. stdout está almacenado en el búfer si mi memoria me sirve bien. Se vacía el almacenamiento intermedio cada vez que se llega al final de la línea:

printf("Should be flushed immediatelly\n"); 

O puede utilizar fflush para limpiar el stdout:

printf("Will be buffered and then flushed"); 
fflush(stdout); 

También puede activar amortiguando fuera mediante el uso de setbuf:

setbuf(stdout, NULL); 
+1

Acabo de probar sus sugerencias pero sin suerte :( –

2

Quizás su biblioteca nativa, por alguna razón, no conozca la consola.
Puede intentar llamar al GetConsole y ver si se devuelve un identificador. Si no puede intentar asignar su propio console para ver si eso funciona.
¡Buena suerte! :-)


Actualización:
escribí una aplicación de ejemplo también (consola de C# aplicación llamando C++ nativo DLL) y tanto el C# Console.WriteLine y el printf nativa aparecerá en la consola ... ¿Cuáles son tan nos falta?
¿Siempre lo ejecuta en modo de depuración? ¿Ve alguna ventana de consola si la ejecuta en modo de lanzamiento?
Actualización 2:
Lo siento, debería decir que veo el texto en la consola, pero si configuro la salida de la Consola en un StreamWriter, como en el ejemplo, solo el texto de WriteConsole va al archivo de salida, el printf s siguen yendo a la pantalla

+1

He actualizado mi pregunta según sus sugerencias. –

+0

Véase también http://stackoverflow.com/questions/432832/what-is-the-different-between-api-functions-allocconsole-and-attachconsole-1 – abatishchev

+0

abatishchev: esa es otra llamada de función aleatoria. No es gracioso, pero lo que realmente está mal con mis llamadas simples printf en primer lugar? –

0

implementar su propio printf (en la parte superior de vsnprintf para cuidar de los detalles sucios) que escribe en la consola:

#include <stdarg.h> 

int printf(const char *fmt, ...) 
{ 
    char buffer[LARGESIZE]; 
    int rv; 
    va_list ap; 
    va_start(ap, fmt); 
    rv = vsnprintf(buffer, sizeof(buffer), fmt, ap); 
    va_end(ap); 

    Console.WriteLine(buffer); 

    return rv; 
} 
+0

Buena idea. Simplemente no lo llames 'printf()' (simplemente porque no lo es). – DevSolar

Cuestiones relacionadas