<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Coders.me &#187; Visual Basic</title>
	<atom:link href="http://www.coders.me/lang/en/category/visual-basic/feed" rel="self" type="application/rss+xml" />
	<link>http://www.coders.me/</link>
	<description>Blog de Informática y Programación</description>
	<lastBuildDate>Mon, 07 Dec 2009 18:48:23 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.1.2</generator>
		<item>
		<title>Escribiendo Aplicaciones de Consola en Visual Basic 6</title>
		<link>http://www.coders.me//lang/en/general/escribiendo-aplicaciones-de-consola-en-visual-basic-6</link>
		<comments>http://www.coders.me//lang/en/general/escribiendo-aplicaciones-de-consola-en-visual-basic-6#comments</comments>
		<pubDate>Mon, 31 Mar 2008 05:50:55 +0000</pubDate>
		<dc:creator>Amir</dc:creator>
				<category><![CDATA[General]]></category>
		<category><![CDATA[Visual Basic]]></category>
		<category><![CDATA[aplicación de consola]]></category>
		<category><![CDATA[pe header]]></category>

		<guid isPermaLink="false">http://www.algoritmatica.com/?p=148</guid>
		<description><![CDATA[<img src="http://www.coders.me/wp-content/uploads/2008/09/general-48x48.jpg" width="48" height="48" alt="" title="General" /><br/><p>Seguro muchos de nosotros alguna vez habremos pensado en escribir programas de consola en Visual Basic pero hemos tenido que migrar a lenguajes como C o Pascal por que como su nombre lo indica este lenguaje es “Visual”.</p>
<p><span id="more-148"></span><br />




</p><p>La realidad es…</p>]]></description>
			<content:encoded><![CDATA[<img src="http://www.coders.me/wp-content/uploads/2008/09/general-48x48.jpg" width="48" height="48" alt="" title="General" /><br/><p>Seguro muchos de nosotros alguna vez habremos pensado en escribir programas de consola en Visual Basic pero hemos tenido que migrar a lenguajes como C o Pascal por que como su nombre lo indica este lenguaje es “Visual”.</p>
<p><span id="more-148"></span><br />
<script type="text/javascript"><!--
google_ad_client = "pub-6896919298908258";
/* Post Abajo Patrocinado Por (Grande) */
google_ad_slot = "5751554033";
google_ad_width = 336;
google_ad_height = 280;
//-->
</script>
<script type="text/javascript"
src="http://pagead2.googlesyndication.com/pagead/show_ads.js">
</script>
<p>La realidad es distinta y en este post, les mostraré la forma de crear aplicaciones que corran en modo Consola sin mostrar el formulario, asumiré que se tienen los siguientes conocimientos:
</p>
<ul>
<li>Visual Basic 6.</li>
<li>Uso de las Win32 API’s.</li>
<li>PE (Portable Executable) Header.</ul>
</li>
</ul>
<h3>Herramientas Utilizadas</h3>
<ul>
<li>Editor Hexadecimal.</li>
<li>PE Editor.</li>
<li>Visual Basic 6.</li>
</ul>
<h3>Aplicaciones de Consola  y la PE Header.</h3>
<blockquote><p>El formato PE es basicamente una estructura de datos que encapsula la información necesaria para el cargador de Windows para gestionar el código de un ejecutable.
</p></blockquote>
<p>
Dentro de un Ejecutable PE, podemos encontrar una estructura que nos servirá para nuestro fin (Crear ejecutables de consola).<br />
La estructura <strong>“IMAGE_OPTIONAL_HEADER”</strong>.
</p>
<pre class="brush: c;">
typedef struct _IMAGE_OPTIONAL_HEADER {
    //
    // Standard fields.
    //

    WORD    Magic;
    BYTE    MajorLinkerVersion;
    BYTE    MinorLinkerVersion;
    DWORD   SizeOfCode;
    DWORD   SizeOfInitializedData;
    DWORD   SizeOfUninitializedData;
    DWORD   AddressOfEntryPoint;
    DWORD   BaseOfCode;
    DWORD   BaseOfData;

    //
    // NT additional fields.
    //

    DWORD   ImageBase;
    DWORD   SectionAlignment;
    DWORD   FileAlignment;
    WORD    MajorOperatingSystemVersion;
    WORD    MinorOperatingSystemVersion;
    WORD    MajorImageVersion;
    WORD    MinorImageVersion;
    WORD    MajorSubsystemVersion;
    WORD    MinorSubsystemVersion;
    DWORD   Win32VersionValue;
    DWORD   SizeOfImage;
    DWORD   SizeOfHeaders;
    DWORD   CheckSum;
    WORD    Subsystem;
    WORD    DllCharacteristics;
    DWORD   SizeOfStackReserve;
    DWORD   SizeOfStackCommit;
    DWORD   SizeOfHeapReserve;
    DWORD   SizeOfHeapCommit;
    DWORD   LoaderFlags;
    DWORD   NumberOfRvaAndSizes;
    IMAGE_DATA_DIRECTORY DataDirectory[IMAGE_NUMBEROF_DIRECTORY_ENTRIES];
} IMAGE_OPTIONAL_HEADER32, *PIMAGE_OPTIONAL_HEADER32;
</pre>
<p>
De toda esta estructura el único dato que nos interesa es el valor “Subsystem”  de 16 bits (2 bytes).<br />
Subsystem puede llevar distintos valores, el valor que contienen las aplicaciones GUI es 2 y las consolas tienen el valor 3.
</p>
<pre class="brush: c;">
#define IMAGE_SUBSYSTEM_WINDOWS_GUI          2   // Image runs in the Windows GUI subsystem.
#define IMAGE_SUBSYSTEM_WINDOWS_CUI          3   // Image runs in the Windows character subsystem.
</pre>
<p>
Por lo tanto modificaremos el valor de los ejecutables que compilemos en Visual Basic, para ello necesitaremos un editor de archivos PE para ubicar el offset del Subsytem y un editor Hexadecimal para modificarlo.
</p>
<h3>Creando la aplicación de Consola</h3>
<p>
Haremos algo sencillo, utilizaremos las APIS para manejar la consola y escribiremos en ella <em>“Hello Override – Algoritmatica has you”</em> y el texto cambiará de color a Verde.</p>
<h3>Apis necesarias:</h3>
<pre class="brush: vb;">
Private Declare Function FreeConsole Lib &quot;kernel32&quot; () As Long
Private Declare Function CloseHandle Lib &quot;kernel32&quot; (ByVal hObject As Long) As Long
Private Declare Function GetStdHandle Lib &quot;kernel32&quot; (ByVal nStdHandle As Long) As Long
Private Declare Function WriteConsole Lib &quot;kernel32&quot; Alias &quot;WriteConsoleA&quot; (ByVal hConsoleOutput As Long, lpBuffer As Any, ByVal nNumberOfCharsToWrite As Long, lpNumberOfCharsWritten As Long, lpReserved As Any) As Long
Private Declare Function SetConsoleTextAttribute Lib &quot;kernel32&quot; (ByVal hConsoleOutput As Long, ByVal wAttributes As Long) As Long
Private Declare Function SetConsoleTitle Lib &quot;kernel32&quot; Alias &quot;SetConsoleTitleA&quot; (ByVal lpConsoleTitle As String) As Long
</pre>
<h3>Constantes</h3>
<pre class="brush: vb;">
Private Const STD_OUTPUT_HANDLE = -11&amp;
Private Const FOREGROUND_GREEN = &amp;H2
</pre>
<h3>Código</h3>
<pre class="brush: vb;">

Private Sub Form_Load()
Form1.Hide ' Ocultamos el formulario
    Dim hConsoleOut As Long
    hConsoleOut = GetStdHandle(STD_OUTPUT_HANDLE) ' Obtenemos el handle de la consola
    If (hConsoleOut) Then
        Dim sTexto As String
        Dim lWritten As Long
        sTexto = &quot;Hello Override - Algorimatica has you!&quot;  ' Texto a mostrar en la consola
        SetConsoleTitle (&quot;Algoritmatica.com&quot;)                    ' Cambiamos el titulo de la consola
        SetConsoleTextAttribute hConsoleOut, FOREGROUND_GREEN  ' Cambiamos el color de texto de las letras
        WriteConsole hConsoleOut, ByVal sTexto, Len(sTexto), lWritten, ByVal 0&amp;   ' Mostramos el texto en la consola
    End If
    'Matamos la consola

    CloseHandle hConsoleOut
    FreeConsole
    End ' fin de ejecución
End Sub
</pre>
<h3>Compilando Código</h3>
<p>
Ahora compilamos nuestro código como lo haríamos de manera normal y generamos nuestro ejecutable, en mi caso lo he llamado <em>test2.exe.</em><br />
Una vez compilado necesitaremos nuestro Editor Pe, en este caso, yo he usado la herramienta <strong>“PEview”.</strong>
</p>
<h3>Buscando Subsystem</h3>
<p>
Abrimos nuestro archivo compilado (Test2.exe) en el Peview y expandemos  el árbol <strong>“IMAGE_NT_HEADERS”</strong> y seleccionamos<strong> “IMAGE_OPTIONAL_HEADER”</strong> ahora del lado derecho buscamos<br />
“Subsystem” y encontramos que se encuentra en el <em>offset 0&#215;00000114.</em>
</p>
<p><img src="http://farm3.static.flickr.com/2012/2375841553_ba36c2b057.jpg?v=0" alt="PE VIEW" /></p>
<h3>Editando fichero y cambiando el valor de Subsystem</h3>
<p>
Ahora abriremos nuestro fichero compilado en un editor hexadecimal, yo he usado WinHex.<br />
Buscaremos la offset 0&#215;00000114 y vemos que tiene el valor 0&#215;02, modificaremos el valor y colocaremos 0&#215;03 lo que hará que el ejecutable corra en modo Consola.
</p>
<p><img src="http://farm3.static.flickr.com/2198/2375841697_d10307aaaa.jpg?v=0" alt="Hexadecimal editing" /><br />
Salvamos el fichero y ahora lo corremos desde el cmd.exe o command.com</p>
<h3>El resultado final es:</h3>
<p><img src="http://farm4.static.flickr.com/3267/2375841791_12ed91c1b1.jpg?v=0" alt="Ejecutable vb6 en consola" /></p>
<h3>Notas finales</h3>
<p>
Como nota final, se podría crear una función que escriba en la consola y otra función que espere por entrada de datos algo así como funciones equivalentes en C como son printf y scanf.<br />
Con esas dos funciones podríamos ya empezar a programar nuestra aplicación en consola</p>
]]></content:encoded>
			<wfw:commentRss>http://www.coders.me//lang/en/general/escribiendo-aplicaciones-de-consola-en-visual-basic-6/feed</wfw:commentRss>
		<slash:comments>5</slash:comments>
		</item>
	</channel>
</rss>

