De acordo com as Leis 12.965/2014 e 13.709/2018, que regulam o uso da Internet e o tratamento de dados pessoais no Brasil, ao me inscrever na newsletter do portal DICAS-L, autorizo o envio de notificações por e-mail ou outros meios e declaro estar ciente e concordar com seus Termos de Uso e Política de Privacidade.

Inclua códigos-fonte de outras linguagens dentro do seu script Perl

Colaboração: Otávio Fernandes

Data de Publicação: 29 de janeiro de 2008

Introdução:

O Inline é um módulo que permite que você acrescente código de outras linguagens de programação diretamente no seu script Perl, salvando-o de ter que escrever dois programas e fazê-los "conversar", gastando muito mais tempo do que se você pudesse simplesmente misturar as linguagens ... mas com a flexibilidade do Perl e a ajuda do Inline você pode. Nas linhas abaixo estarei demonstrando de forma descontraída e objetiva como isso é possível.

Fazendo a Instalação:

Antes de fazermos uso do Inline, temos que fazer a instalação, para isso separei duas formas de realizá-la; uma via CPAN, a qual eu recomendo, pois é muito mais fácil centralizar os pacotes do Perl em uma única ferramenta, e também podemos ter sempre a versão mais nova de cada módulo, o que nem sempre acontece com os pacotes pré-compilados; e outra via apt-get:

CPAN:

Com a mesma simplicidade dos códigos em Perl, utilizamos a CPAN: Neste primeiro passo, chamamos o prompt para execução de comandos:

perl -MCPAN -e shell

Logo em seguida devemos requisitar a instalação do módulo Inline:

install Inline

Pronto. Observe os retornos e se necessário, trate os erros que aparecerão no meio do caminho. Não entenderei mais esta parte pois este não é o nosso foco.

Debian:

No Debian, com a utilização do apt-get, as coisas ficam tão fáceis quanto na CPAN, basta executar o seguinte comando (como root, ou com permissões de super-usuário):

  # apt-get update
  # apt-get install libc-scan-perl libinline-octave-perl libinline-perl libtest-inline-perl

E esperar o retorno do comando, aqui nos meus testes eu não tive nenhum problema com os dois tipos de instalação.

Exemplos Práticos:

Em um determinado momento da nossa vida de programadores, seja profissionalmente ou apenas por diversão, fez-se necessário a execução de algum(s) método(s) de uma biblioteca natural de outra linguagem, o que para alguns casos, é aparentemente inviável, mas com a flexibilidade do Perl, e as inovações dos módulos presente na CPAN isso é mais do que possível, é fácil e muito prático. Nos exemplos abaixo, estaremos chamando métodos da nossa "libteste", a qual está presente no diretório "/usr/lib" e tem seus headers no diretório "/usr/include", o teste.h, para dificultar as coisas, quando instânciamos a libteste, precisamos ter no nosso fonte declarado uma estrutura, a qual servirá para troca de dados, o nome dela é treetst (bem sugestivo :-P):

Utilizando o Inline C, podemos fazer uso das funções de duas formas distintas:

  1. Escrevendo um trecho de código C que faça a chamada da função, e retorne seu conteúdo para o nosso script:
      01| #!/usr/bin/perl
      02|
      03| use scrict;
      04| use warnings;
      05|
      06| # fazendo a chamada direta da função escrita no código abaixo
      07| my $retr = WrapFTest();
      08|
      09| # imprimindo na stdout o retorno da função WrapFTest
      10| print $retr, "\n";
      11|
      12| # declarando a nossa libteste como parâmetro para compilação
      13| use Inline C => Config => ENABLE => AUTOWRAP => LIBS => '-lteste';
      14| # da próxima linha até a string "END_OF_C_CODE" tudo é código C
      15| use Inline C => << 'END_OF_C_CODE';
      16|
      17| #include <teste.h>
      18|
      19| struct treetst *p1, *p1;
      20|
      21| int WrapFTest () { return Teste(); }
      22|
      23| END_OF_C_CODE
    
    Segue o comentário das linhas mais importantes deste código, na mesma organização que o interpretador e o Inline o fazem:

    [16-22]

    Junção deste código à trecho pré existente de código C, preparado para o enxerto de novas linhas de código. Atente que o código tem todos os requisitos para compilar a executar a libteste, ou seja, a presença do "include" de seu header "teste.h" e também apresenta da estrutura "treetst", necessária para troca de dados (não tratados aqui);

    [13]

    Configurando como será a compilação do código C, com o uso da "-lteste" junto com o gcc, esta linha que permite ao compilador saber qual biblioteca estamos procurando. Para maiores detalhes, execute o comando "# ldconfig -v" e faça uma breve análise dos resultados retornados;

    [07]

    Fazendo a execução da função "WrapFTest()", a qual tem o papel de intermediar a execução da função que nos interessa, a "Teste()". Fazemos uso desta função porque não temos acesso direto à libteste, apenas ao pseudo-código que geramos no bloco de linhas 16 a 22;

    [10]

    Imprimindo o retorno da função "Teste()". Lembrando que o retorno, ou parâmetros, ou até estruturas de dados podem trocados entre o script e o código C (outras linguagens também).

    Pronto, executamos uma chamada na libteste através do nosso pequeno, porém eficiente, código ANSI C, veremos no próximo exemplo como fazer isso de forma direta.

  2. Podemos instânciar as funções diretamente da biblioteca e fazer uso no nosso script:
      01| #!/usr/bin/perl -w
      02|
      03| use warnings;
      04| use strict;
      05|
      06| use Inline C => Config => ENABLE => AUTOWRAP => LIBS => "-lteste";
      07| use Inline C => q{ struct treetst *p1, *p2; };
      08| use Inline C => q{ int Teste(); };
      09|
      10| my $retr = Teste();
      l1|
      12| print $retr, "\n";
    
    Neste exemplo estamos acessando a libteste diretamente do nosso script em Perl, sem a ajuda de código para enxerto, apenas com o protótipo das funções (vide o arquivo header para maiores detalhes). Segue o comentário e explicação das linhas mais influentes do nosso script:

    [07]

    Declarando a estrutura que vamos utilizar para trocar os dados com a libteste, assim como fariamos em um código C comum (vide Caso 1);

    [08]

    Protótipo da função "Teste()", presente no header "/usar/include/teste.h";

    [10]

    Eureca. Estamos acessando a função "Teste()" diretamente do nosso script :-);

    [12]

    Imprimindo na saída padrão o retorno da função "Teste()";

Bibliografia:

Otávio Fernandes, exercendo atualmente o cargo Programador Sênior e Gerente de Projetos, tem larga experiência em appliances para servidores de E-Mail e Anti-SPAM, fluência em linguagens como ANSI C e C++, porem um aprendiz em Perl. Contato otaviof at gmail dot com.

Adicionar comentário

* Campos obrigatórios
5000
Powered by Commentics

Comentários

Nenhum comentário ainda. Seja o primeiro!


Veja a relação completa dos artigos de Otávio Fernandes