El blog de Juan Palómez

13 mayo 2015

Missing Perl binary (perl.exe) on Cygwin

Filed under: Uncategorized — Etiquetas: , — thisisoneball @ 00:23

Symptoms:
  • Packages ‘perl’ and ‘perl_base’ are installed but /usr/bin/perl is missing
  • cygcheck -c perl  says OK
  • cygcheck -c perl_base says Incomplete

Solution:

  • Run Cygwin setup, click Keep, look for perl_base package and set it to Reinstall

18 abril 2013

Memory usage treemap / WinDirStat for memory

Filed under: Uncategorized — Etiquetas: , , , , — thisisoneball @ 15:11

Warning: this is a quick hack, it’s not complete and it has bugs. Feel free to correct them and send me the changes.
Also, unlike WinDirStat, measuring memory usage is more difficult than measuring disk space. There are many different memory sizes for one process (Private Bytes, Working Set, Virtual Size, …), this just uses the output of the Windows tasklist command.

memoria

It’s a Perl program that tries to run that command, parses the output, and uses Google Charts Treemap to render the output.
It prints the HTML to stdout so the best way to run it is:
perl memoryusage.pl > memoryusage.html && start memoryusage.html

my %groups = ();
my $output;

my $output_pre = "
        <html>
          <head>
            <script type='text/javascript' src='https://www.google.com/jsapi'></script>
            <script type='text/javascript'>
              google.load('visualization', '1', {packages:['treemap']});
              google.setOnLoadCallback(drawChart);
              function drawChart() {
                  // Create and populate the data table.
                  var data = google.visualization.arrayToDataTable([
                    ['Process', 'Parent', 'Size'],
                    ['root',    null,                 0],
";

my $output_post = "
                  ]);

                  // Create and draw the visualization.
                  var treemap = new google.visualization.TreeMap(document.getElementById('chart_div'));
                  treemap.draw(data, {
                    minColor: 'red',
                    midColor: '#ddd',
                    maxColor: '#0d0',
                    headerHeight: 15,
                    fontColor: 'black',
                    showScale: true});
                }
        </script>
  </head>

  <body>
    <div id='chart_div' style='width: 900px; height: 500px;'></div>
  </body>
</html>
";

open TASKLIST, "tasklist /nh /fo CSV |" or die "Can't execute tasklist command $!\n";
while (<TASKLIST>) {
        if (m/"(.+)","(.+)",".+",".+","(.+) KB?"/) {
                $name = $1;
                $pid  = $2;
                $size = $3;
                $size =~ s/\.//;
                $output .= "['$pid','$name',$size],\n";
                $groups{"$name"} = 1;
        }
}

close TASKLIST;

while ( my ($key, $value) = each(%groups) ) {
        $output .= "['$key','root',0],\n";
}

chop $output;
chop $output;

print $output_pre . $output . $output_post;

26 enero 2009

Dependencias entre ficheros fuente

Filed under: Uncategorized — Etiquetas: , , , — thisisoneball @ 17:25

Otra de las múltiples carencias de MySQL es que no tiene un sistema de dependencias entre objetos. Por ejemplo, un procedimiento almacenado que isnerta en una tabla, o lee de una vista, o una vista que lee de otras tablas o vistas, etc…

Te permite borrar o cambiar de nombre un objeto aun cuando está siendo referenciado desde otro sitio. Esto hay quien lo ve como una ventaja (es más cómodo siempre que sepas lo que estás haciendo). Pero para un proyecto medianamente grande y en el que trabajen varias personas se hace inmantenible.

Siempre queda la opción de hacer un programa que lea los ficheros fuente, y sepa encontrar ahí dónde se referencian otros objetos o ficheros fuente. He estado buscando en Internet algo hecho y solo he visto alguna cosa para ficheros .c y .h. Asi que he preparado este script como solución rápida. De momento solo busca en ficheros fuente de Perl y de procedimientos almacenados de MySQL.

Va dibujando un arbol de las llamadas entre unos y otros. Por ejemplo:

perl1.pl
	perl2.pl
	mysql1.sql
	mysql2.sql
		mysql4.sql
	mysql5.sql

en este caso el fichero perl1.pl llama a un programa Perl (perl2) y a 3 procedimientos almacenados (mysql1, mysql2 y mysql5), y mysql2 a su vez llama a mysql4

Los parámetros del programa son el fichero fuente a partir del cual se empieza a buscar, y la lista de directorios en los que buscar, y se ejecuta desde el directorio que contiene a éstos. Ej:

--raiz/
    |--perl/
        |-- perl1.pl
	|-- perl2.pl
    |--mysql/
        |-- mysql1.pl

En este caso se llamaría desde ‘raiz’, por ejemplo con:

dependencias.pl perl1.pl {perl,mysql}

Requiere el módulo File::Grep, que sirve para lo mismo que el comando grep. Es bastante incómodo de utilizar y probablemente habría sido mejor utilizar simplemente grep en un script de shell o de Perl.

El programa es fácilmente adaptable a otros lenguajes. Solo hay que especificar cómo se hacen las llamadas a otros scripts (do, call, system, …)

Se agradecen ampliaciones y correcciones.

#!/usr/bin/perl

use File::Grep qw( fgrep );

die "Uso: dependencias.pl <archivo fuente inicial> {directorio1,directorio2}...\n\n" unless @ARGV == 2;

my $directorios = $ARGV[1];

busca($ARGV[0], "");

sub busca {

	my $ocurrencia;
	my %matches;
	my $match_key;
	foreach $ocurrencia (fgrep { /(call|do).*\(/i } glob "$directorios/$_[0]") {
		%matches = %{${$ocurrencia}{'matches'}};			# matches es un hash que contiene las lineas encontradas
		foreach (sort keys %matches) {
			if ($matches{$_} =~ m/call\s+(.+)\(/i) {		# llamadas a procedimientos almacenados MySQL
				print "$_[1]$1.sql\n";
				busca("$1.sql", $_[1]."    ");
			} elsif ($matches{$_} =~ m/do.*\'(.+)\'/i) {		# llamadas a scripts Perl
				print "$_[1]$1\n";
				busca("$1", $_[1]."    ");
			}
		}
	}

}

17 junio 2008

Calcular distancias entre dos puntos dados en grados

Filed under: Uncategorized — Etiquetas: , , , , — thisisoneball @ 16:20

Las coordenadas latitud/longitud vienen en grados, con lo cual no se pueden medir distancias. En cambio el sistema UTM sirve también para localizar un punto concreto en la superficie de la Tierra, y viene expresado en metros. Con lo cual solo hace falta pasarlas de un sistema a otro.
Este código (Perl) pasa las coordenadas a UTM con el módulo Geo-Coordinates-UTM y luego calcula la distancia con el teorema de Pitágoras. Previamente tienes que tener las coordenadas de un punto en $latitud1 y $longitud1 y las del otro en $latitud2 y $longitud2:


use Geo::Coordinates::UTM;...

($zona, $este1, $norte1) = latlon_to_utm ("WGS-84", $latitud1, $longitud1);
($zona, $este2, $norte2) = latlon_to_utm ("WGS-84", $latitud2, $longitud2);
$distancia = sqrt((($este2 - $este1)**2) + (($norte2 - $norte1)**2));

De forma manual se puede usar simplemente la regla de Google Earth. El código anterior es útil si tienes que procesar series grandes de coordenadas.
Se puede configurar Google Earth para que muestre las coordenadas en UTM en vez de en grados: Herramientas > Opciones > Vista 3D > Universal Transversal de Mercator.

Creo que se puede calcular sin pasar a UTM, con las fórmulas de geometría de la esfera. Tendría cierto error ya que la Tierra no es esférica, pero para distancias pequeñas no debería importar.

Problema: El sistema UTM va por cuadrantes. Este código sólo sirve entre dos coordenadas que estén en el mismo cuadrante.

Blog de WordPress.com.