Como você força um processo a liberar os dados gravados em um descritor de arquivo aberto no Linux?

4

Eu tenho um processo binário (sem fontes disponíveis) em execução em um sistema Linux embarcado. O processo abre um arquivo de log (/tmp/dmaosd.log) onde ele registra o que está fazendo.

O problema é que o log é atualizado em partes (cerca de 1000 bytes de cada vez), por isso não posso ver o log em tempo real com tail -f.

Gostaria de saber se existe alguma maneira de forçar o processo em execução a liberar seus dados (com base no acesso / proc / 1234 / fd / 3) sem ter acesso às suas fontes e sem enviar nenhum sinal para ele (eu não sou certeza de quais sinais ele suporta nem o que eles devem fazer).

O processo em questão é um OSD para um media player, e as informações de registro geralmente mostram quais elementos são selecionados / mostrados na tela, então seria bom ter os dados o mais rápido possível.

Obrigado!

    
por Mad_Ady 09.01.2013 / 10:31

1 resposta

6

Depende realmente de onde está o buffer: se o aplicativo usa seu próprio buffer de registro, não há como forçar um flush.

Se o armazenamento em buffer é feito pela biblioteca C, você pode usar LD_PRELOAD para desativar o armazenamento em buffer. Supondo que o programa esteja usando fopen() para abrir seu arquivo de log, você pode fazer algo assim:

#define _GNU_SOURCE 1
#include <dlfcn.h>
#include <stdio.h>

static FILE* (*libc_fopen)(char const *, char const *);

FILE * fopen(char const *name, char const *mode) {
    FILE *ret;
    if (!libc_fopen)
        libc_fopen = dlsym(RTLD_NEXT, "fopen");

    ret = libc_fopen(name, mode);
    if (!ret)
        return ret;

    setvbuf(ret, NULL, _IONBF, 0);

    return ret;
}

Compile como uma biblioteca compartilhada e use LD_PRELOAD para "injetar" no programa:

LD_PRELOAD=./nobuffering.so myprogram

Se desejar, você também pode verificar o nome do arquivo e alterar o buffer apenas para o arquivo de registro em que está interessado.

    
por 24.05.2013 / 11:53