[ << ] | [ < ] | [ Acima ] | [ > ] | [ >> ] | [Topo] | [Conteúdo] | [Índice] | [ ? ] |
O presente capítulo descreve a forma que funções GSL relatam e controlam erros. Por meio do exame à informação de situação atual retornada por toda função você pode determinar se a função obteve sucesso ou falhou, e se a função tiver falhado você pode encontrar qual foi a precisa causa da falha. Você pode também definir suas próprias funções de controle de erros para modificar o comportamento padrão da biblioteca.
As funções descritas nessa seção são declaradas no arquivo de cabeçalho ‘gsl_errno.h’.
3.1 Relatórios de Erro | ||
3.2 Códigos de Erro | ||
3.3 Controladores de Erro | ||
3.4 Usando relatório de erro da GSL em suas próprias funções | ||
3.5 Exemplos |
[ << ] | [ < ] | [ Acima ] | [ > ] | [ >> ] | [Topo] | [Conteúdo] | [Índice] | [ ? ] |
A biblioteca segue as convenções de relato de erro para linhas de execução segura da
biblioteca de linha de execução POSIX. Funções retornam um código de erro diferente de zero para
indicar um erro e 0
para indicar sucesso.
int status = gsl_function (...) if (status) { /* an error occurred */ ..... /* status value specifies the type of error */ }
As rotinas reportam um erro sempre que elas não puderem executar a tarefa requisitada delas. Por exemplo, uma função de busca por uma raíz pode retornar um código de erro diferente de zero se não puder convergir com a exatidão requisitada, ou exceder um limite numérico de repetições. Situações como essas são uma ocorrência normal quando usamos qualquer biblioteca matemática e você deve verificar a situação atual do retorno de funções que você chama.
sempre que uma rotina informar um erro o valor de retorno especifica o tipo
de erro. O valor de retorno é semelhante ao valor da variável
errno
na biblioteca C. Quem fez a chamada pode examinar o código de retorno
e decidir que ação executar, inclusive ignorando o erro se esse erro não for
considerado grave.
Adicionalmente para informar erros por meio do código de retorno a biblioteca também tem uma
função de controle de erro chamada gsl_error
. Essa função é chamada por
outras funções de biblioteca quando elas informam um erro, somente antes dessas outras funções
retornarem à função chamadora. O comportamento padrão do controlador de erro é
mostrar uma mensagem e interromper o programa,
gsl: file.c:67: ERROR: invalid argument supplied by user Default GSL error handler invoked. Aborted
O objetivo do controlador gsl_error
é fornecer uma função
onde um ponto de parada possa ser ajustado o qual irá capturar erros de biblioteca quando
executando dentro de um depurador de erros. A função controladora de erro não foi pensada para ser usada em programas de
produção, os quais devem controlar quaisquer erros usando os códigos de retorno.
[ << ] | [ < ] | [ Acima ] | [ > ] | [ >> ] | [Topo] | [Conteúdo] | [Índice] | [ ? ] |
Os códigos de erros numéricos retornados através das funções de biblioteca são definidos no
arquivo ‘gsl_errno.h’. Todos os códigos de erro possuem o prefixo GSL_
e
expandem para valores inteiros do tipo constante e são diferentes de zero. códigos de erros acima de 1024 são
reservados para aplicações, e não são usados pela biblioteca. Muitos dos
códigos de erro usam o mesmo nome básico do correspondente código de erro
na biblioteca C. Aqui estão alguns dos códigos de erro mais comuns,
Erro de domínio; usado por funções matemáticas quando um valor de argumento está fora domínio sobre o qual a função que está sendo usada está definida (da mesma forma que EDOM na biblioteca C)
Erro de intevalo; usado pr funções matemáticas quando o valor do resultado não é representável pelo fato de muito grande ou muito pequeno (da mesma forma que ERANGE na biblioteca C)
Sem memória disponível. O sistema não pode alocar mais memória virtual
pelo fato de sua capacidade ter sido toda usada (da mesma forma que ENOMEM na biblioteca C). esse erro
é informado quando a rotina GSL encontra problemas ao tentar
alocar memória com malloc
.
Argumento inválido. É usada para indicar vários tipos de problema com a informação de argumentos inadequados enviados a uma função de biblioteca (da mesma forma que EINVAL na biblioteca C library).
Os códigos de erro podem ser convertidos em uma mensagem de erro usando a
função gsl_strerror
.
Essa função retorna um apontador para uma sequência de caracteres descrevendo o código de erro gsl_errno. Por exemplo,
printf ("erro: %s\n", gsl_strerror (status));
não irá mostrar uma mensagem de erro com erro: erro de intervalo de saída
para um
valor de situação atual de GSL_ERANGE
.
[ << ] | [ < ] | [ Acima ] | [ > ] | [ >> ] | [Topo] | [Conteúdo] | [Índice] | [ ? ] |
O comportamento padrão do controlador de erro da GSL é mostrar uma mensagem
curta e chamar abort
. Quando esse comportamento padrão for adotado por um programa que estiver sendo usado
irá parar o programa criando um arquivo core-dump mesmo se uma rotina de biblioteca informar um erro.
O objetivo desse comportamento é ser um padrão de erro seguro para programas que não verificam
a situação atual de retorno de rotinas de biblioteca (não encorajamos você a escrever
programas dessa forma).
Se você desabilitar o controlador de erro padrão a responsabilidade é toda e exclusivamente sua de verificar os valores de retorno de rotinas e manipulá-los você mesmo. você pode também personalizar o comportamento de erro fornecendo um novo controlador de erro. Por exemplo, um controlador de erro alternativo pode gravar em um arquivo, ignorar certas condições de erro (tais como valores muito pequenos), ou iniciar o depurador e anexar o depurador ao processo atual quando um erro ocorrer.
Todos os controladores de erro da GSL possuem o tipo gsl_error_handler_t
, o qual é
definido em ‘gsl_errno.h’,
Esse é o tipo das funções controladoras de erro da GSL. Ao controlador de erro irá
ser informado quatro argumentos os quais especificam a razão para o erro (uma
sequência de caracteres), o nome do arquivo fonte no qual o erro ocorreu (também uma
sequência de caracteres), o número da linha daquele arquivo (um inteiro) e o número do erro
(um inteiro). O arquivo fonte e o número de linha são ajustados na hora da compilação
usando as diretivas __FILE__
e __LINE__
no
pré-processador. Uma função controladora de erro retorna o tipo de dado void
.
Funções controladoras de erro devem ser definidas como segue,
void handler (const char * reason, const char * file, int line, int gsl_errno)
Para requisitar o uso de seu próprio controlador de erro você precisa chamar a
função gsl_set_error_handler
a qual é também declarada em
‘gsl_errno.h’,
Essa função ajusta um novo controlador de erro, new_handler, para as rotinas de biblioteca da GSL. O controlador antigo é guardado em memória (de forma que você pode recuperá-lo mais tarde). Note que o apontador para uma função controladora de erro definida pelo usuário é armazenado em uma variável estática, de forma que existe um único controlador de erro por programa. Essa função não deve ser usada em programas com suporte a múltiplas linhas de execução exceto para ajustar um controlador de erro que abrange completamente um programa a partir de uma linha de execução principal. O exemplo seguinte mostra como ajustar e retaurar um novo controlador de erro,
/* grava o controlador original, instala um novo controlador */ old_handler = gsl_set_error_handler (&my_handler); /* o código uso o novo controlador */ ..... /* restaura o controlador original */ gsl_set_error_handler (old_handler);
Para usar o comportamento padrão (abort
em caso de erro) ajuste o controlador
de erro para NULL
,
old_handler = gsl_set_error_handler (NULL);
Essa função desabilita o controlador de erro por meio da definição de um controlador de erro que não faz nada. Isso irá fazer com que o programa continue após qualquer erro, de forma que o valor de retorno de qualquer rotina de biblioteca da GSL deva ser verificado. Esse é o comportamento recomendado para programas de produção. O controlador antigo é guardado em memória (de forma que você pode restaurar o controlador antigo posteriormente).
O comportamento de erro pode ser mudado para aplicações específicas através da
recompilação da biblioteca com uma definição personalizada da
macro GSL_ERROR
no arquivo ‘gsl_errno.h’.
[ << ] | [ < ] | [ Acima ] | [ > ] | [ >> ] | [Topo] | [Conteúdo] | [Índice] | [ ? ] |
Se você está escrevendo funções numéricas em um programa que também usa código da GSL você pode achar conveniente adotar as mesmas conveções de relatório de erros adotadas pela biblioteca GSL.
Para informar um erro você precisa chamar a função gsl_error
com uma
sequência de caracteres descrevendo o erro e então retornar um código de erro apropriado
a partir de gsl_errno.h
, ou um valor especial, tal com NaN
. Por
conveniencia o arquivo ‘gsl_errno.h’ define duas macros que realizam
esses passos:
Essa macro informa um erro usando as convenções da GSL e retorna um
valor da situação atual de gsl_errno
. Expande para o seguinte fragmento de código,
gsl_error (reason, __FILE__, __LINE__, gsl_errno); return gsl_errno;
A definição de macro em ‘gsl_errno.h’ atualmente abrange o código
em um bloco do { ... } while (0)
para prevenir possíveis
problemas de valores de retorno.
Aqui está um exemplo de como a macro pode ser usada para informar que uma
rotina não encontrou uma tolerância requisitada. Para informar o erro a
rotina precisa retornar o código de erro GSL_ETOL
.
if (residual > tolerancia) { GSL_ERROR("residual excede tolerancia", GSL_ETOL); }
Essa macro é a mesma que GSL_ERROR
mas retorna um valor definido
pelo usuário armazenado em valor ao invés de um código de erro. GSL_ERROR_VAL
pode ser usada para
funções matemáticas que retornam um valor em ponto flutuante.
O seguinte exemplo mostra como retornar um NaN
em uma singularidade
matemática usando a macro GSL_ERROR_VAL
,
if (x == 0) { GSL_ERROR_VAL("o argumento localiza-se em uma singularidade", GSL_ERANGE, GSL_NAN); }
[ << ] | [ < ] | [ Acima ] | [ > ] | [ >> ] | [Topo] | [Conteúdo] | [Índice] | [ ? ] |
Aqui está um exemplo de algum código que verifica o valor de retorno de uma função onde um erro pode ser informado,
#include <stdio.h> #include <gsl/gsl_errno.h> #include <gsl/gsl_fft_complex.h> ... int status; size_t n = 37; gsl_set_error_handler_off(); status = gsl_fft_complex_radix2_forward (data, stride, n); if (status) { if (status == GSL_EINVAL) { fprintf (stderr, "argumento invalido, n=%d\n", n); } else { fprintf (stderr, "falhou, gsl_errno=%d\n", status); } exit (-1); } ...
A função gsl_fft_complex_radix2
somente aceita comprimentos de inteiros
que são uma potência de dois. Se a variável n
não for uma potência de
dois então a chamada para a função de biblioteca irá retornar GSL_EINVAL
,
indicando que o comprimento do argumento é inválido. A chamada de função a
gsl_set_error_handler_off
impede o controlador de erro padrão de
abortar o programa. A cláusula else
captura quaisquer outros erros
possíveis.
[ << ] | [ >> ] | [Topo] | [Conteúdo] | [Índice] | [ ? ] |
Esse documento foi gerado em 23 de Julho de 2013 usando texi2html 5.0.