jueves, 29 de julio de 2010

Colores en printf

Se puede imprimir en la pantalla en colores al usar la funcion printf (....) como se muestra en este ejemplo:

/*********color_printf.c*************/
#include < stdio.h >
int main ()
{
printf ("\033[30m Salida en color: Negro\n");
printf ("\033[31m Salida en color: Rojo\n");
printf ("\033[32m Salida en color: Verde\n");
printf ("\033[33m Salida en color: Amarillo\n");
printf ("\033[34m Salida en color: Azul\n");
return 0;
}
/************************************/
Compilacion:
gcc -Wall -o color_printf color_printf.c
Salida en pantalla:

Salida en color: Negro
Salida en color: Rojo
Salida en color: Verde
Salida en color: Amarillo
Salida en color: Azul

domingo, 25 de julio de 2010

The UNIX® System

Si quiere conocer mas acerca de los sistemas operativos UNIX , puede visitar el sitio http://www.unix.org donde encontrara mucha informacion de sus especificaciones e historia

Matar Procesos

Un ejemplo en C de como matar procesos usando para ello la llamada al sistema int system(const char *string); que permite la ejecucion de una orden del interprete de comandos (shell).
Para mas informacion sobre esta funcion en su manual " man system " o si quiere este manual en castellano " man -L es system ".

/********matar_proceso.c********/
#include < stdio.h >
#include < string.h >
#include < stdlib.h >

int main(int argc, char **argv)
{
char *tmpStr;
int i,len,lenB;
char *Kill="kill -9 ";
char *killtotal=NULL;

for (i = 0; i < argc; i++)
{
tmpStr = argv[i];
if ( (strcmp(tmpStr,"-h")==0)||(strcmp(tmpStr,"--help")==0) ||\
(strcmp(tmpStr,"--usage")==0)||(strcmp(tmpStr,"-help")==0) || argc==1)
{
printf("\n");
printf("Usar: matar_proceso --pid IDPROCESO \n");
printf(" --help\n");
printf(" --version Version\n");
printf(" --pid\n");
printf("\n");
exit(0);
}

if((strcmp(tmpStr,"--pid")==0))
{
len=strlen(argv[i+1]);
lenB=strlen(Kill);
killtotal=(char*)malloc(len+lenB);
memset(killtotal,'\0',(len+lenB));
strcpy(killtotal,Kill);
strcat(killtotal,argv[i+1]);
}
if((strcmp(tmpStr,"--version")==0))
{
printf("0.1\n");
exit(0);
}
}
if(killtotal!=NULL)
{
printf("Matando el proceso --> %s\n",killtotal);
system(killtotal);
free(killtotal);
}
return 1;
}


/********************/
Compilacion:
gcc -Wall -O2 -o matar_proceso matar_proceso.c

jueves, 22 de julio de 2010

Manejo de colores y fuentes en Xlib

El manejo de colores y de fuentes en Xlib puede ser algo confuso o complejo para algunos que recien comienzan a programar unsando las librerias base del Xserver las Xlib.
En este ejemplo se muestra como crear una ventana y luego en ella colocar texto con un tamaño y color determinado.

/**********x11_1.c*************/

#include < X11/Xlib.h >
#include < X11/Xutil.h >
#include < stdio.h >
#include < string.h >

/*
Retorna el color mas proximo del mapa de colores
*/
unsigned long Buscar_color_nombre( Display *display, char *Nombre )
{
XColor color, temp;
XAllocNamedColor( display,DefaultColormap(display,DefaultScreen(display)),Nombre, &color, &temp );
return color.pixel;
}


int main()
{
Display *display;
Window window;
GC gc;
Font fuente;
char *Texto1 = "Test: Fuentes en Xlib";
char *Texto2 = "Color Rojo";
char *Texto3 = "Color Verde";

display = XOpenDisplay( NULL );
window = XCreateSimpleWindow( display,DefaultRootWindow( display ),100, 100, 300, 200, 1, 0, 1 );
XMapWindow( display, window );

gc = XCreateGC( display, window, 0, NULL );
fuente = XLoadFont( display, "9x15" );
XSetForeground(display, gc, Buscar_color_nombre(display, "white"));
XSetFont( display, gc, fuente );
XDrawString( display, window, gc, 10, 50, Texto1, strlen(Texto1) );
XSetForeground(display, gc, Buscar_color_nombre(display, "red"));
XDrawString( display, window, gc, 10, 80, Texto2, strlen(Texto2) );
XSetForeground(display, gc, Buscar_color_nombre(display, "green"));
XDrawString( display, window, gc, 10, 110, Texto3, strlen(Texto3) );

XFlush( display );
getchar();
}


/******************************/
Compilacion:
gcc -o x11_1 x11_1.c -lX11

miércoles, 21 de julio de 2010

Señales en C

Un pequeño programa que implementa el manejo de señales en c en base a estructuras y punteros.

/**********signal_c.c**************/
#include

struct Punteros_a_Funciones{
void (*leer)();
};
typedef struct Punteros_a_Funciones puntero_a_func;
typedef void* data;
#define VOID_POINTER (void*)
#define SIGNAL_FUC(f) ((SignalFunc)f)
typedef void (*SignalFunc) (void);

void signal_1()
{
printf("signal_1\n");
}

void signal_2()
{
printf("signal_2\n");
}
puntero_a_func Pasando_punteros(SignalFunc funci)
{
puntero_a_func puntero = { SIGNAL_FUC(funci)};
return puntero;
}
int main()
{
puntero_a_func Voides;
SignalFunc funci;

funci=signal_1;
Voides = Pasando_punteros(funci);
Voides.leer();

funci=signal_2;
Voides = Pasando_punteros(funci);
Voides.leer();
return 0;
}

/**********************************/
Compilacion:
gcc -o signal_c signal_c.c

domingo, 18 de julio de 2010

Modificar la posicion en pantalla de una aplicacion X en ejecucion

Se puede modificar algunos parametros de una aplicacion X en ejecucion para ello solo es necesario conocer la ID de esa aplicacion. El programa xwininfo nos puede ayudar para este proposito (lease su manual --> man xwininfo) su modo de uso es el siguiente.
Al ejecutar en consola el xwininfo este cambiara el cursor a una forma de cruz lo que nos indica que debemos seleccionar la aplicacion X que queremos saber sus propiedades, solo haga crick en la ventana de la aplicacion y xwininfo mostrara una salida como la siguiente:
------------------------
xwininfo: Please select the window about which you
would like information by clicking the
mouse in that window.

xwininfo: Window id: 0x1a0000d "xterm"

Absolute upper-left X: 5
Absolute upper-left Y: 25
Relative upper-left X: 0
Relative upper-left Y: 0
Width: 501
Height: 316
Depth: 16
Visual Class: TrueColor
Border width: 0
Class: InputOutput
Colormap: 0x20 (installed)
Bit Gravity State: NorthWestGravity
Window Gravity State: NorthWestGravity
Backing Store State: NotUseful
Save Under State: no
Map State: IsViewable
Override Redirect State: no
Corners: +5+25 -774+25 -774-683 +5-683
-geometry 80x24+1+1

-----------------------
Lo que interesa es la ID de la aplicacion que se encuentra en la siguiente linea
xwininfo: Window id: 0x1a0000d "xterm"
La iD sera ==> 0x1a0000d
Pero para el uso dela aplicacion C que permitira cambiarle sus propiedades es necesario usar un valor decimal ya que lo que muestra por defecto la aplicacion xwininfo es en hexadecimal. Para ello solo hay que agregarle el siguiente parametro:
xwininfo -int
Y mostrara el siguiente resultado
xwininfo: Window id: 27262989 "xterm"
Ya tenemos la informacion necesaria que es la ID de la aplicacion X , lo siguiente es desarrollar el programa en C que por el momento solo permitira cambiar la posicion en pantalla de la ventana ya luego en los siguientes post se le agregara nuevas funcionalidades.

/*---------xcambiargeo.c-----------*/
#include < stdio.h >
#include < stdlib.h >
#include < X11/Xlib.h >
#include < X11/Xutil.h >

int main(int argc,char *argv[])
{
Display *display;
int XwinID,Xwin_nuevaX,Xwin_nuevaY;

if(argc != 4){
fprintf(stderr,"Usar:%s nueva_posicion_x nueva_posicion_y XwinID\n",argv[0]);
return 0;
}

Xwin_nuevaX=atoi(argv[1]);
Xwin_nuevaY=atoi(argv[2]);
XwinID=atoi(argv[3]);

printf("nueva_posicion_x=%d nueva_posicion_y=%d Xaplicacion=%d \n",Xwin_nuevaX,Xwin_nuevaY,XwinID);

display = XOpenDisplay( NULL );
if(display==NULL)
{
printf("Error al abrir display\n");
return 0;
}
XMoveWindow( display,XwinID,Xwin_nuevaX,Xwin_nuevaY);
XCloseDisplay(display);
return 1;
}

/*---------------------------------*/
Compilando:
gcc -o xcambiargeo xcambiargeo.c -lX11
Uso:
./xcambiargeo nueva_posicion_x nueva_posicion_y XwinID
./xcambiargeo 200 300 27262989
Donde:
nueva_posicion_x => Es la posicion x en la pantalla
nueva_posicion_y => Es la posicion y en la pantalla
XwinID => La ID de la aplicacion X o la ventana
Al ejecutar el programa xcambiargeo , se observara que la aplicacion X cambiara de un lugar a otro en la pantalla.

Comparacion de dos archivos

Cuando se quiere comparar dos archivos del mismo tamaño y el resultado de la comparacion grabarlo en algun archivo se puede implementar algun programa en C para realizar esta funcion.
El programa que se muestra acontinuacion permite comparar 2 archivos y la diferencia es decir toda aquella informacion que no esta presente en alguno de estos 2 archivos se graba en otro.
Su modo de uso es el siguiente:
./comparar_archivos archivo_uno_a_comparar archivo_dos_a_comparar archivo_diferencia

"archivo_diferencia" es donde se grabara todos los bits diferentes entre ambos archivos.

/*-----------comparar_archivos.c----------------*/

#include < stdio.h >
#include < stdlib.h >
#include < fcntl.h >
#include < unistd.h >
#include < sys/types.h >
#include < sys/stat.h >
#include < errno.h >


int main(int argc, char *argv[])
{
int fd,fdB,fdC,x,y;
char *fila_uno, *fila_dos,*fila_nueva;
struct stat sbuf;
int z;
char c[1];
char cc[1];

if (argc != 4) {
fprintf(stderr, "usar: programa fila_uno fila_dos fichero_a_crear\n");
exit(1);
}
fila_uno=argv[1];
fila_dos=argv[2];
fila_nueva=argv[3];

if ((fd = open(fila_uno,O_RDONLY )) == -1) {
perror("open fila_uno");
exit(1);
}

if ((fdB = open(fila_dos,O_RDONLY)) == -1) {
perror("open fila_dos");
exit(1);
}

if ((fdC = open(fila_nueva, O_RDWR | O_CREAT)) == -1) {
perror("open fila_nueva");
exit(1);
}

if (stat(fila_uno, &sbuf) == -1) {
perror("stat");
exit(1);
}

for(x=0;x<(sbuf.st_size);x++)
{
z=lseek(fd,x,SEEK_SET);
y=lseek(fdB,x,SEEK_SET);
read(fd,c,1);
read(fdB,cc,1);
if( *c!=*cc)
{
write(fdC,c,1);
}
}
return 0;
}


/*----------------------------------------------*/

Compilar:
gcc -o comparar_archivos comparar_archivos.c

sábado, 17 de julio de 2010

Depurar binarios con strace y ltrace

Como siempre cuando se programa es necesario tener diferente herramientas para depuracion como strace y ltrace.
strace permite interceptar y grabar las llamadas al sistema. Mas informacion consulte al manual "man strace"

ltrace permite interceptar y grabar las llamadas a las librerias dinamicas. Mas informacion consulte al manual "man ltrace"

Uso de strace:
strace -i -o binariofile.strace binariofile
Donde:
binariofile.strace: puede ser cualquier archivo donde se grabara la informacion que proporciona strace.
binariofile: Es cualquier binario que se quiere depurar
Salida que se muestra contiene:
[ffffe410] execve("./mc", ["./mc"], [/* 65 vars */]) = 0
[b7f8544b] brk(0) = 0x812a000
[b7f85db1] access("/etc/ld.so.preload", R_OK) = -1 ENOENT (No such file or directory)
[b7f85c74] open("/etc/ld.so.cache", O_RDONLY) = 3
[b7f85c3e] fstat64(3, {st_mode=S_IFREG|0644, st_size=102714, ...}) = 0
[b7f86273] mmap2(NULL, 102714, PROT_READ, MAP_PRIVATE, 3, 0) = 0xb7f57000
[b7f85cad] close(3) = 0
[b7f85c74] open("/opt/gnome/lib/libgmodule-2.0.so.0", O_RDONLY) = 3
[b7f85cf4] read(3, "\177ELF\1\1\1\0\0\0\0\0\0\0\0\0\3\0\3\0\1\0\0\0`\r\0\0004\0\0\0"..., 512) = 512
[b7f85c3e] fstat64(3, {st_mode=S_IFREG|0755, st_size=13928, ...}) = 0
[b7f86273] mmap2(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0xb7f56000
[b7f86273] mmap2(NULL, 16664, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0xb7f51000
[b7f85ef9] fadvise64(3, 0, 16664, POSIX_FADV_WILLNEED) = 0
[b7f86273] mmap2(0xb7f54000, 8192, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x2) = 0xb7f54000
[b7f85cad] close(3) = 0
[b7f85c74] open("/lib/libdl.so.2", O_RDONLY) = 3
[b7f85cf4] read(3, "\177ELF\1\1\1\0\0\0\0\0\0\0\0\0\3\0\3\0\1\0\0\0\240\n\0\0004\0\0\0"..., 512) = 512
[b7f85c3e] fstat64(3, {st_mode=S_IFREG|0755, st_size=10288, ...}) = 0
[b7f86273] mmap2(NULL, 12412, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0xb7f4d000
[b7f85ef9] fadvise64(3, 0, 12412, POSIX_FADV_WILLNEED) = 0
[b7f86273] mmap2(0xb7f4f000, 8192, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x1) = 0xb7f4f000
[b7f85cad] close(3) = 0
...........................
.....................

Uso de ltrace:
ltrace -i -o binariofile.ltrace binariofile
Donde:
binariofile.ltrace: puede ser cualquier archivo donde se grabara la informacion que proporciona strace.
binariofile: Es cualquier binario que se quiere depurar
Salida que se muestra contiene:
[0x805cc21] __libc_start_main(0x8082670, 1, 0xbfe522f4, 0x80ee4f0, 0x80ee4e0
[0x808269e] getenv("LANG") = "POSIX"
[0x80826ac] strlen("POSIX") = 5
[0x8082969] strcasecmp("POSIX", "UTF-8") = -5
[0x80826c9] setlocale(6, "") = "LC_CTYPE=en_US.UTF-8;LC_NUMERIC="...
[0x80826dd] bindtextdomain("mc", "/usr/share/locale") = "/usr/share/locale"
[0x80826e9] textdomain("mc") = "mc"
[0x809b354] getenv("TMPDIR") = NULL
[0x809b369] getuid() = 0
[0x809b371] getpwuid(0, 0xbfe520dc, 0xbfe520ac, 130953, 55) = 0xb7d269b8
[0x809b39f] g_snprintf(0x81185a0, 64, 0x80f6906, 0x80f6901, 0x812b080) = 12
[0x809afe1] strlen("/tmp/mc-root") = 12
[0x809b032] strlen("/tmp/mc-root") = 12
[0x809b3c3] __lxstat64(3, "/tmp/mc-root", 0xbfe520b8) = 0
[0x809b5a0] getuid() = 0
[0x809b550] setenv("MC_TMPDIR", "/tmp/mc-root", 1) = 0
[0x80826fa] getenv("SHELL") = "/bin/bash"
..............
.............

Mostrar simbolos de un binario

Para conocer que simbolos esta usando un binario puede hacer uso de la aplicacion nm que es parte del paquete binutils.
Para mas informacion consulte su manual --> man nm
Uso:
nm binariofile
Muestra una salida como se indica a continuacion:

0807a370 t add2hotlist
0807b0f0 T add2hotlist_cmd
08085f60 t add2panelize
080d98b0 t add_a_service
080e19f0 T add_char_string
080e1910 t add_dos_char
08097ca0 T add_hook
080798c0 t add_name_to_list
0807dc30 T add_select_channel
0806a4c0 T add_widget
0807a920 t add_widgets_i18n
081262e0 b addr_buf.9806
0805d530 t advanced_chown_callback
08126e90 B alarm_colors
080f8e60 r all_filters
08129a48 B allones_ip
08118d44 B altered_hex_mode
08118d48 B altered_magic_flag
08118d4c B altered_nroff_flag
08113750 B alternate_plus_minus
081117b8 b and_mask
080f679f r app_text
08125424 B append_log
0807d130 T application_keypad_mode
.........
.........

Mostrar informacion de binarios ELF

Si necesita conocer informacion de algun binario ELF , puede usar la aplicacion readelf.
Para mas informacion lea su manual --> man readelf
Uso:
readelf -a binariofile
Muestra una salida como esta:


ELF Header:
Magic: 7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00
Class: ELF32
Data: 2's complement, little endian
Version: 1 (current)
OS/ABI: UNIX - System V
ABI Version: 0
Type: EXEC (Executable file)
Machine: Intel 80386
Version: 0x1
Entry point address: 0x805cc00
Start of program headers: 52 (bytes into file)
Start of section headers: 824720 (bytes into file)
Flags: 0x0
Size of this header: 52 (bytes)
Size of program headers: 32 (bytes)
Number of program headers: 10
Size of section headers: 40 (bytes)
Number of section headers: 31
Section header string table index: 28

Section Headers:
[Nr] Name Type Addr Off Size ES Flg Lk Inf Al
[ 0] NULL 00000000 000000 000000 00 0 0 0
[ 1] .interp PROGBITS 08048174 000174 000013 00 A 0 0 1
[ 2] .note.ABI-tag NOTE 08048188 000188 000020 00 A 0 0 4
[ 3] .note.SuSE NOTE 080481a8 0001a8 000018 00 A 0 0 4
...................
....................

Linux Programacion: Tips 1

Algunas herramientas que les puede ser utiles:
a) Eliminacion de simbolos o secciones usadas en depuracion que puede contener algun binario.
Mas informacion en su manual --> man objcopy
objcopy -g binariofile


b) Desamblador(dissasembler) de binarios
Mas informacion en su manual --> man objdump
objdump -d binariofile

Muestra una salida como esta:

0805b620 <_init>:
805b620: 55 push %ebp
805b621: 89 e5 mov %esp,%ebp
805b623: 53 push %ebx
805b624: 83 ec 04 sub $0x4,%esp
805b627: e8 00 00 00 00 call 805b62c <_init+0xc>
805b62c: 5b pop %ebx
805b62d: 81 c3 c8 19 0b 00 add $0xb19c8,%ebx
805b633: 8b 93 fc ff ff ff mov -0x4(%ebx),%edx
805b639: 85 d2 test %edx,%edx
805b63b: 74 05 je 805b642 <_init+0x22>
805b63d: e8 9e 02 00 00 call 805b8e0 <__gmon_start__@plt>
805b642: e8 19 16 00 00 call 805cc60
805b647: e8 04 2f 09 00 call 80ee550 <__do_global_ctors_aux>
805b64c: 58 pop %eax
805b64d: 5b pop %ebx
805b64e: c9 leave
805b64f: c3 ret
Disassembly of section .plt:
...................
................

miércoles, 14 de julio de 2010

Convertir programas C / C++ a actionscript

Adobe alchemy es una herramienta que proporciona Adobe que facilita el uso de librerias o codigo hecho en C o C++ para ser utilizado en Flash 10.
Desde hace algun tiempo lo estoy usando y me a sido de gran utilidad, cuando me entere de este proyecto de adobe al leer su documentacion me parecio una gran solucion en el tema del rendimiento segun Adobe el proyecto Alchemy permitia el acceso a bajo nivel que facilitaba o mejoraba en gran medida algunas falencias de Flash que era el consumo de memoria y rendimiento ,pero luego de usarlo y buscar mas informacion sobre este tema me di con la ingrata sorpresa que todo lo que argumentaban la gente de Adobe era falso.
No mejoraba el rendimiento y hacia un uso mejor de la memoria, aveces hacia todo lo contrario pero al menos me facilitaba el uso de algunas librerias hechas en ANSI C que eran facilmente portadas para ser usados en Flash 10.
Adobe alchemy esta disponible para linux y es uno de los pocos proyectos libres que tiene Adobe.

domingo, 4 de julio de 2010

Programacion en Linux

Este blog tratara todo lo referente a la programcion en el sistema operativo Linux/GNU, durante mucho tiempo programo en linux en varios lenguajes ademas de usar herramientas en su mayoria libres y algunas propietarias.