Latest entries

Simular enumeraciones en Python

written by uve

14 May 2012

Estoy ahora mismo trabajando con Python y me acabo de encontrar que disponer de una enumeración me vendría muy bien. Así que, después de investigar un rato, he encontrado dos formas distintas y muy prácticas para hacer enumeraciones.

Estilo C

La primera opción, es hacerlas como se hacen en C. Variables enteras globales:

(GATEWAY_CLASS, FORWARDING_CLASS, PARSE_CLASS) = range(1, 4)

El problema de esta solución, es que en cualquier momento se puede modificar el valor de cualquiera de estas variables, con las consecuencias que esto conlleva.

Estilo Java

En Java, cuando declaramos una enumeración, debemos acceder a través del nombre de la enumeración. Por tanto, para simular este comportamiento en Python, necesitamos una clase:

class RoutingClassType(type):
    (GATEWAY_CLASS,
        FORWARDING_CLASS,
        PARSE_CLASS) = range(1, 4)

Así, ahora tendríamos que acceder así:

RoutingClassType.GATEWAY_CLASS

Aunque esta solución sigue presentando el mismo problema que la solución anterior, lo podemos solucionar creando un nuevo tipo que impida modificar sus atributos:

class EnumType(type):
    def __setattr__(self, name, value):
        raise ValueError

Y ahora bastará con definir nuestra enumeración de la siguiente forma:

class RoutingClassType(type):
    __metaclass__ = EnumType
   
    (GATEWAY_CLASS,
        FORWARDING_CLASS,
        PARSE_CLASS) = range(1, 4)

Full entry >>

SystemError: error return without exception set

written by uve

11 April 2012

Esto se puede deber a que se ha devuelto NULL en una función en la que se debería devolver algo (None por ejemplo):

static PyObject*
example(PyObject *self, PyObject* args, PyObject* kwargs)
{
    // do something
    return NULL;
}

se corrige de la siguiente forma:

static PyObject*
example(PyObject *self, PyObject* args, PyObject* kwargs)
{
    // do something
    Py_RETURN_NONE;
}

o porque al lazar una excepción, no hemos indicado de que excepción se trata:

static PyObject*
example(PyObject *self, PyObject* args, PyObject* kwargs)
{
    PyObject* var;
    // ...
    if(!PyBool_Check(var))
    {
        return NULL;
    }
}

y se corrige:

static PyObject*
example(PyObject *self, PyObject* args, PyObject* kwargs)
{
    PyObject* var;
    // ...
    if(!PyBool_Check(var))
    {
        PyErr_SetString(PyExc_TypeError, "Not boolean");
        return NULL;
    }
}

Full entry >>

npm: Error: Required package: options(latest) not found. (Found: ["0.0.3"])

written by uve

7 April 2012

Hace unos días que descubrí substance.io y estos días me he decidido a instalarlo. A la hora de instalar unos módulos para Node.js con el comando npm me he encontrado con este error:

npm ERR! install failed Error: Required package: options(latest) not found. (Found: ["0.0.3"])
npm ERR! install failed (required by: ws@0.4.12)
npm ERR! install failed     at /usr/share/npm/lib/build.js:192:19
npm ERR! install failed     at cb (/usr/share/npm/lib/utils/graceful-fs.js:32:9)
npm ERR! Error: Required package: options(latest) not found. (Found: ["0.0.3"])
npm ERR! (required by: ws@0.4.12)
npm ERR!     at /usr/share/npm/lib/build.js:192:19
npm ERR!     at cb (/usr/share/npm/lib/utils/graceful-fs.js:32:9)
npm ERR! Report this *entire* log at <http://github.com/isaacs/npm/issues>
npm ERR! or email it to <npm-@googlegroups.com>
npm ERR! Just tweeting a tiny part of the error will not be helpful.
npm not ok

Parece que el problema está en la versión de npm que viene instalada en Ubuntu, que está desactualizada. Así que hay que desinstalar el que viene en repositorios e instalarlo directamente.

Para simplificar el proceso podemos usar este script. Es necesario tener instalado curl.

Full entry >>

¿Cómo utilizar TCP_NODELAY?

written by uve

2 April 2012

Llevaba cerca de dos días con un problema implementando el subscriptor MQTT. Aún no está hecho el diagrama de flujo ya que de momento estoy probando que las llamadas de la biblioteca funcionan. El escenario es el siguiente:

  1. mqtt_connect
  2. mqtt_subscribe
  3. mqtt_unsubscribe
  4. mqtt_disconnect

Conectamos el cliente, nos subscribimos a un topic, nos desubscribimos y desconectamos el cliente. Algo que a priori es sencillamente elemental.

Para comprobar que todo esto funciona he hecho uso del script para Wireshark que ya comenté. Pero el caso es que estaba encontrando errores en Wireshark que no eran lógicos. Yo mandaba un paquete de 17bytes y Wireshark decía que el paquete tenía 19bytes. ¿Qué estaba pasando aquí?

Full entry >>

Synaptic: No se pudieron analizar o abrir las listas de paquetes o el archivo de estado

written by uve

1 April 2012

Al abrir Synaptic me he encontrado con el siguiete error:

E: Encountered a section with no Package: header
E: Problem with MergeList /var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_precise-security_main_binary-i386_Packages
E: No se pudieron analizar o abrir las listas de paquetes o el archivo de estado.
E: _cache->open() failed, please report.

La solución:

$ sudo rm /var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_precise-security_main_binary-i386_Packages

Full entry >>

Bindings Python para bibliotecas C: Argumentos (Parte 4)

written by uve

28 March 2012

Continuando con el ejemplo de ayer, hoy voy a explicar cómo podemos parsear los parámetros de entrada. El estado actual es que hemos definido unos prototipos y los hemos añadido al módulo. Ahora vamos a darle contenido a las funciones add y hello.

Ejemplo en GitHub: mema_methods.

Full entry >>

Argumentos en Python

written by uve

28 March 2012

Para los programadores de C, C++, Java, ... puede resultar un tanto extraño la forma de gestionar los parámetros que tiene Python.

Voy a explicar en esta entrada los tipos de parámetros y cómo podemos hacer uso de ellos.

Full entry >>

Bindings Python para bibliotecas C: Métodos (Parte 3)

written by uve

27 March 2012

Ayer explicaba cómo se monta una estructura básica para crear un módulo. Pero para que el módulo sirva para algo, tendremos que añadir funciones.

Ahora vamos a ver cómo podemos crear nuevas funciones y cómo integrarlas al módulo mema. El objetivo para hoy será crear dos funciones: hello y add.

El resultado debería ser algo similar a lo siguiente:

>>> import mema
>>> mema.hello()
Hello mema!
>>> mema.hello('Vicente')
Hello Vicente!
>>>
>>> from mema import add
>>> add(1, 2)
3
>>> add(400, 4)
404
>>>

Ejemplo en GitHub: mema_methods.

Full entry >>

Preparar un Alix para exposiciones: Gráficos y gestión de energía (Parte 3)

written by uve

26 March 2012

Una vez que tenemos listo todo el tema de gráficos . y automatizado el proceso de arranque, toca empezar con detalles estéticos. Para ello, debemos evitar situaciones cómo un salvapantallas o que el monitor se apague.

Recordad que estamos en un entorno en el que no tenemos teclado ni ratón, por lo que en seguida, el sistema operativo pensará que no hay actividad en el equipo.

Full entry >>

Bindings Python para bibliotecas C: Módulos y compilación (Parte 2)

written by uve

26 March 2012

La semana pasada empecé ha hablar sobre los Bindings en Python. Hoy vamos a ver cómo es una estructura muy básica, cómo compilar y probar que todo funciona.

Un problema que me estoy encontrando, es que el API C de Python ha ido cambiando con las versiones. Entonces, muchos ejemplos que he encontrado no compilan y hay código muy diferente por ahí.

Inicialmente voy a centrarme en Python 2.7 (última versión de la rama 2.x) y si encuentro tiempo, haré lo mismo para Python 3.

Ejemplo en GitHub: mema_bare.

Full entry >>

Bindings Python para bibliotecas C: ¿Qué son? (Parte 1)

written by uve

23 March 2012

Hoy voy a hablar acerca de bindings para Python. Un binding es un módulo Python, escrito en lenguaje C, que permite realizar llamadas a funciones en C desde un script hecho en Python. Se puede ver como un "puente" desde C a Python.

Pueden existir distintos motivos para desear hacer un binding. En principio, puede parecer un poco contraproducente, ya que se pierde portablidad

Entonces, ¿por qué crear un binding? Bien es sabido por todos que C es más eficiente que Python, por tanto, si se trata de una parte crítica de una aplicación, perfectametne se puede hacer el procesamiento en C y dejar Python para la lógica.

Otra razón es aprovechar código existente en C. Como comenté, estoy trabajando en libemqtt, la cuál está escrita en C. Podría hacer una nueva implementación completa en Python, pero teniendo el código disponible, lo lógico es hacer un binding.

Los próximos días intentaré escribir una pequeña guía sobre cómo hacer un binding para esta bibliotecta.

Actualización (27/03/2012): He creado un repositorio en GitHub con los ejemplos que estoy implementando:

https://github.com/menudoproblema/menudoproblema-examples/tree/master/python/bindings

Full entry >>

Una implementación ligera de MQTT: libemqtt

written by uve

23 March 2012

Hace unas semanas empecé a trabajar en una librería MQTT, con dispositivos empotrados en mente. La idea es que esta librería provea de las funciones de MQTT y así los clientes puedan encargarse de la gestión de la red. Con esto se puede reutilizar este código para distintas plataformas, cómo pueden ser Arduino ó LPC1768, pero también desde Linux.

Todo empezó cuando estaba evaluando distintas alternativas. Por casualidad me encontré con liblwmqtt en Google Code, desarrollada por Filipe Varela. Tras hablar con él, decidí hacer un fork y así nace libemqtt.

El código está disponible en Github:

https://github.com/menudoproblema/libemqtt

Full entry >>

MQTT dissector for Wireshark

written by uve

15 March 2012

Acabo de terminar una primera versión del script que parsea MQTT para mostrar la información sobre este protocolo en Wireshark.

Lo he dejado colgado de Github, por si alguien está interesado en el tema.

Full entry >>

Lanzar un script Lua con Wireshark

written by uve

15 March 2012

Wireshark incluye el parseo de la inmensa mayoría de protocolos de red que existen, pero cómo es evidente, no todos. Estas semanas estoy trabajando con MQTT y para este protocolo hay un soporte muy muy básico.

Para lanzar el script, basta con ejecutar lo siguiente:

$ wireshark -X lua_script:mqtt.lua

donde mqtt.lua es el nombre de mi script.

Full entry >>

Habilitar scripts Lua en Wireshark como root

written by uve

14 March 2012

Ahora mismo estoy trabajando en un script escrito en Lua para parsear información de un protocolo en en Wireshark. Necestio hacer unas pruebas como superusuario, pero por defecto, los scripts están deshabilitados para root.

Para habilitar el soporte a Lua, necesitamos editar el siguiente script:

sudo nano /usr/share/wireshark/init.lua

y comentar la siguiente función:

-- disable potentialy harmful lua functions when running superuser
--if running_superuser then
    --local disabled_lib = {}
    --setmetatable(disabled_lib,{ __index = function() error("this package has been disabled") end } );

    --dofile = function() error("dofile has been disabled") end
    --loadfile = function() error("loadfile has been disabled") end
    --loadlib = function() error("loadlib has been disabled") end
    --require = function() error("require has been disabled") end
    --os = disabled_lib
    --io = disabled_lib
    --file = disabled_lib
--end

Full entry >>

La teoría es cuando crees saber algo, pero no funciona.
La práctica es cuando algo funciona, pero no sabes por qué.
Los programadores combinan la teoría y la práctica:
Nada funciona y no saben por qué.