Jorge Serrano
  • Home

Porqué es bueno eliminar la refencia al ensamblado Microsoft.VisualBasic.dll en nuestros proyectos (I)

  • By jorge
  • Nov-4-2008
  • Sin categoría
  • 9 Comments.

 


Introducción


En la última entrada de mi blog, escribí acerca de como eliminar la referencia al ensamblado Microsoft.VisualBasic.dll de nuestros proyectos.


En esa entrada, hubo algunas personas que dieron sus opiniones dentro del apartado de comentarios, algo que agradezco muchísimo, ya que siempre es importante la interactuación de la gente en un blog donde no suele haber un diálogo, sino un intercambio de opiniones o puntos de vista, y los razonamientos y pensamientos se hacen a trompicones.


Las dudas razonables…


Dentro de esos comentarios hubo uno iniciado por delm en el que afirmaba que le daba mucha lástima que se gastara energía en investigar cosas como la que indicaba en mi entrada, y dudaba que esos esfuerzos sirvieran para algo.


Desde luego, que cualquier investigación o análisis sirve, incluso si las conclusiones de esos estudios son nulos. Es positivo que se realicen estudios de todo tipo (con cierto criterio claro está) con el fin de aprender más acerca de las tecnologías y su uso.


Pero no solo es positivo en el campo de la investigación y su uso, sino que a veces es incluso hasta importante u obligatorio.


Por esa razón supongo, delm nos comentaba igualmente que se fundamentara las afirmaciones que se realizan en mi entrada con estudios o profiling en una o varias aplicaciones de un tamaño decente para ver si realmente vale la pena.


A mí me gustaría por otro lado, que delm también realizara esos estudios para fundamentar sus opiniones contrarias. Así nos enriqueceríamos todos.


No obstante, yo ya hice algunos estudios sobre esto hace tiempo, pero ni los tenía a mano, ni sinceramente, me encontraba con ganas de repetirlos debido al poco tiempo libre que tenía para hacer unos estudios concienzudos. Sin embargo, he sacado algo de tiempo para escribir esta segunda entrada y comentar un pequeño y espero que simbólico estudio que he hecho con el fin u objetivo de demostrar el porqué puede ser interesante eliminar al referencia de Microsoft.VisualBasic.dll y usar en su lugar las librerías de .NET.


Lo más sensato es hacer un estudio muchísimo más riguroso, pero espero que este pequeño estudio ofrezca algo de luz a quienes dudan de si es positivo o no eliminar la referencia a Microsoft.VisualBasic.dll.


Recordando…


Recordad, que cuando se llama a un método o función de Microsoft.VisualBasic.dll, ésta se convierte a su método o función equivalente dentro de .NET, lo cuál genera de alguna manera ciertas penalizaciones en el rendimiento de nuestras aplicaciones.


Demostrando…


La pequeña demostración (siento mucho no haber podido hacer una demostración mucho más completa como me hubiera gustado) es la siguiente:


He creado dos clases exactamente iguales en funcionalidad, aunque distintas en cuanto al código escrito, ya que una de ellas se basa en las funciones de VB 6 de Microsoft.VisualBasic.dll y el otro código, se basa en las funciones propias de .NET.


Para estudiar el profiling, me he apoyado en la herramienta JetBrains dotTrace.


Y así, empezamos a codificar la primera clase que he llamado WithReference.


El código de esta primera clase con funciones típicas de VB 6 para .NET es el siguiente:


WithReference.Class1 (Class1.vb):







Namespace WithReference

    
Public Class Class1

        
Public Function DeleteSpaces(ByVal data As String) As String
            Return Trim(data)
        
End Function

        Public Function TakeLeftRightText(ByVal data As String) As String
            Return Left(data, 1) & Right(data, 1)
        
End Function

        Public Function TransformTextMid(ByVal data As String) As String
            Dim auxiliarText As String = «»
            For I As Byte = 1 To Len(data)
                auxiliarText &= Mid(data, I, 1)
            
Next
            Return auxiliarText
        
End Function

        Public Function TransformTextReplace(ByVal data As String, _

            ByVal findCharacter As String, ByVal replaceCharacter As String) As String
            Return Replace(data, findCharacter, replaceCharacter)
        
End Function

        Public Function TransformTextReverse(ByVal data As String) As String
            Return StrReverse(data)
        
End Function

        Public Function TransformTextUpper(ByVal data As String) As String
            Return UCase(data)
        
End Function

        Public Function TransformTextLower(ByVal data As String) As String
            Return LCase(data)
        
End Function

        Public Function GetCharacterPosition(ByVal data As String, ByVal searchText As String) As Byte
            Return InStr(data, searchText)
        
End Function

        Public Sub TestConversion()
            
Dim auxiliarText As String = «»
            For i As Integer = 0 To 10000
                
If i Mod 2 = 0 Then
                    ‘ Convert to String
                    auxiliarText &= Conversion.Int(i).ToString
                
Else
                    ‘ Convert to Integer (Int32)
                    auxiliarText &= Conversion.Str(i)
                
End If
            Next
        End Sub

    End Class ‘ Class1

End Namespace ‘ WithReference


A la segunda clase la he llamado WithoutReference.
El código de la segunda clase con funciones propias de .NET equivalentes a las usadas en la clase anterior es el siguiente:


WithoutReference.Class1 (Class1.vb):







Namespace WithoutReference

    
Public Class Class1

        
Public Function DeleteSpaces(ByVal data As String) As String
            Return data.Trim
        
End Function

        Public Function TakeLeftRightText(ByVal data As String) As String
            Return data.Substring(1, 1) & data.Substring(data.Length – 1, 1)
        
End Function

        Public Function TransformTextMid(ByVal data As String) As String
            Dim auxiliarText As String = «»
            For I As Byte = 0 To data.Length – 1
                auxiliarText &= data.Substring(I, 1)
            
Next
            Return auxiliarText
        
End Function

        Public Function TransformTextReplace(ByVal data As String, _

            ByVal findCharacter As String, ByVal replaceCharacter As String) As String
            Return data.Replace(findCharacter, replaceCharacter)
        
End Function

        Public Function TransformTextReverse(ByVal data As String) As String
            Dim charArray(data.Length) As Char
            For i As Byte = 0 To data.Length – 1
                charArray(i) = data(data.Length – (i + 1))
            
Next
            Return New String(charArray)
        
End Function

        Public Function TransformTextUpper(ByVal data As String) As String
            Return data.ToUpper
        
End Function

        Public Function TransformTextLower(ByVal data As String) As String
            Return data.ToLower
        
End Function

        Public Function GetCharacterPosition(ByVal data As String, ByVal searchText As String) As Byte
            Return data.IndexOf(searchText, 1)
        
End Function

        Public Sub TestConversion()
            
Dim auxiliarText As String = «»
            For i As Integer = 0 To 10000
                
If i Mod 2 = 0 Then
                    ‘ Convert to String
                    auxiliarText &= Convert.ToInt32(i).ToString
                
Else
                    ‘ Convert to Integer (Int32)
                    auxiliarText &= Convert.ToString(i)
                
End If
            Next
        End Sub

    End Class ‘ Class1

End Namespace ‘ WithoutReference


Finalmente he compilado las clases. WithReference con Visual Studio 2008, y WithoutReference siguiendo el patrón de la entrada anterior donde mostraba como compilar una clase con .NET eliminando las referencias a Microsoft.VisualBasic.dll.


La diferencia de tamaños entre las clases son:



  • WithReference.dll (11,5 Kb)

  • WithoutReference.dll (4,5 Kb)

Además de los tamaños de las clases, existen más diferencias en tiempo de ejecución tal y como veremos a continuación.


Para este experimento, he iniciado una aplicación Windows con C# y con un control Button, al que he agregado una referencia con el ensamblado WithReference.dll.
Dentro del código del formulario windows he escrito el siguiente código:


Aplicación Windows (MainForm.cs):







private void btnTestProfiler_Click(object sender, EventArgs e)
{
    
this.Text = «Proceso iniciado…»;
    
this.Enabled = false;
    WithReference.
Class1 classTest = new WithReference.Class1();
    
for (int i = 0; i < 100; i++)
    {
        
string result;
        result = classTest.DeleteSpaces(
» Testing «);
        
byte position;
        position = classTest.GetCharacterPosition(
«Testing», «i»);
        result = classTest.TakeLeftRightText(
«Testing»);
        classTest.TestConversion();
        result = classTest.TransformTextLower(
«ReSuLtS»);
        result = classTest.TransformTextUpper(
«ReSuLtS»);
        result = classTest.TransformTextMid(
«Text to extract letter by letter»);
        result = classTest.TransformTextReplace(
«This is a sample text, to replace it by other different text.», «a», «n»);
        result = classTest.TransformTextReverse(
«This is a sample text, to do the reverse of this text.»);
    }
    
this.Text = «Proceso finalizado.»;
    
this.Enabled = true;
}


He generado el fichero ejecutable y he copiado el ejecutable y la librería en un directorio aparte.


Una vez hecho esto, he repetido el proceso quitando la referencia a WithReference.dll y agregando una referencia al ensamblado WithoutReference.dll.


El código de la aplicación para este segundo caso es el siguiente:


Aplicación Windows (MainForm.cs):







private void btnTestProfiler_Click(object sender, EventArgs e)
{
    
this.Text = «Proceso iniciado…»;
    
this.Enabled = false;
    WithoutReference.
Class1 classTest = new WithoutReference.Class1();
    
for (int i = 0; i < 100; i++)
    {
        
string result;
        result = classTest.DeleteSpaces(
» Testing «);
        
byte position;
        position = classTest.GetCharacterPosition(
«Testing», «i»);
        result = classTest.TakeLeftRightText(
«Testing»);
        classTest.TestConversion();
        result = classTest.TransformTextLower(
«ReSuLtS»);
        result = classTest.TransformTextUpper(
«ReSuLtS»);
        result = classTest.TransformTextMid(
«Text to extract letter by letter»);
        result = classTest.TransformTextReplace(
«This is a sample text, to replace it by other different text.», «a», «n»);
        result = classTest.TransformTextReverse(
«This is a sample text, to do the reverse of this text.»);
    }
    
this.Text = «Proceso finalizado.»;
    
this.Enabled = true;
}


He vuelto a compilar el proyecto y lo he apartado en otro directorio junto a la librería del ensamblado WithoutReference.dll.


De esta manera, tengo los dos programas listos para ser procesados con la herramienta de rendimiento y profiling.


Estudiando comportamientos…


He arrancado la herramienta JetBrains dotTrace y he ejecutado el primer ejecutable (con el ensamblado WithReference.dll) y he obtenido unos datos muy diferentes a los que muestra el segundo ejecutable (con el ensamblado WithoutReference.dll).


Los datos obtenidos del uso de WithReference.dll los he denominado DatosCon.



Los datos obtenidos del uso de WithoutReference.dll los he denominado DatosSin.


 


En este punto, lo que tenemos que hacer es estudiar los comportamientos de los dos ensamblados.


En el caso del uso del ensamblado con referencias a Microsoft.VisualBasic.dll, vemos que el proceso de ejecución nos ha durado 24.445 ms, y el proceso principal del control Button, 20.292 ms.


Por su parte, el ensamblado sin referencia a Microsoft.VisualBasic.dll, ha tardado en el proceso general 17.877 ms, mientras que en el proceso principal del control Button, el tiempo que ha tomado es de 15.827 ms.


Algunas conclusiones…


Las conclusiones a simple vista son bastante claras.


El ensamblado que no tiene referencia a Microsoft.VisualBasic.dll, tiene un menor tamaño en su ensamblado y es más rápido en su ejecución.


De todos los modos, tengo pensado agregar alguna entrada más que tendrá por objetivo estudiar algunos de los resultados obtenidos en estas pruebas, y mirar un poco el código intermedio de ambos ensamblados.


Espero que esto, ayude a clarificar aún más mis afirmaciones, las cuales no son verdades absolutas, pero sí pueden ser consideradas por algunos con un poco más de fundamento.

Comments

9 Responsesso far

  1. anonymous dice:
    4 noviembre, 2008 a las 11:15 pm

    Muy buen aporte nuevamente Jorge, voy a ir practicando con las clases .NET para ver las diferencias en mis proyectos.

    Por cierto el software para Checkear el comportamiento de ambos ensamblados muy bueno voy a echarle un vistazo.

    Saludos.
    Francisco J.

    Responder
  2. anonymous dice:
    4 noviembre, 2008 a las 11:56 pm

    Solo puedo decir que…. muchas gracias..

    Con gente como tú aprendemos TOD@S

    Responder
  3. ohernandez dice:
    5 noviembre, 2008 a las 2:26 am

    Excelente, Jorgito!

    Esto más o menos coincide con lo que yo pensaba sobre el tema: una capa intermedia que no aporta más que malas prácticas de programación!

    Abrazo – Octavio

    Responder
  4. anonymous dice:
    5 noviembre, 2008 a las 8:58 am

    Me ha gustado tu enfoque empírico. Para los programadores de gestión (contabilidades, facturación) no viene a deciornos mucho, pero una cosa está clara, para los programadores que no sean de gestión y que usen VB.NET y necesiten de una optimización del entorno (rendimiento, buenas practicas, etc…) este artículo tiene mucho que decirles.

    Felicidades Jorge.

    PD No me deja evaluarte el articulo pasando el mouse por las estrellitas, tengo iexplorer 8.0 por si te sirve, pero la calif para mi son 4 estrellas

    Responder
  5. jorge dice:
    5 noviembre, 2008 a las 4:17 pm

    Hola Julio,

    es extraño que no se pueda votar.

    Sobre tu comentario, te debo decir que esto que comento puede afectar a cualquier tipo de programador. No es necesario ser programador de gestión o no para que esto nos pueda afectar.

    Date cuenta que dentro de Microsoft.VisualBasic.dll hay instrucciones que afectan no solo a campos texto, sino también a cálculos matemáticos, por lo que sí podría afectar a soluciones Software de tipo contrable, administrativo o de facturación.

    Muchas gracias por comentar Julio. 🙂

    Responder
  6. anonymous dice:
    5 noviembre, 2008 a las 4:21 pm

    No entiendo por qué un programador de gestión no puede hacer las cosas bien y optimizar sus aplicaciones y ofrecer un buen rendimiento en éstas…

    Responder
  7. victorgonzalez dice:
    13 noviembre, 2008 a las 9:47 am

    Gracias por este «manual de buenas prácticas para usuarios de VB6″… 😉

    Muchas veces, el mantener una compatibilidad hacia atrás nos ayuda a «ir más rápido» y comenzar con un nuevo soporte o lenguaje, pero a la larga realmente nos «retrasa» y nos mantiene con extructuras y funciones anticuadas.

    Creo que no es cuestión de optimización para software de Gestión o no, es simplemente una optimización y buenas prácticas de uso de un lenguaje de «última generación» (observa que lo he puesto entre comillado).

    Ahora, lo que tenemos que hacer es quitar la referencia a esta DLL e ir adaptando el software y esperar que para futuras ediciones de VS se pueda eliminar del compilador.

    PD: Sería bueno hacer un manual de correspondencia entre las funciones más utilizadas de VB6 y su equivalente en VB.Net, para que todos los anticuados (yo me incluyo) del VB6 sepamos como sacar el máximo provecho a .Net y olvidar esta DLL.

    Responder
  8. anonymous dice:
    13 noviembre, 2008 a las 4:56 pm

    Esta bien el ejemplo siempre una capa intermedia penaliza el rendimiento.Pero, solo haces comprobaciones con cadenas y estas en .Net estan muy mal optimizadas de ello la existencia de stringbuilder. No puede ser que sea la mala optimizacion de las cadenas de caracteres las que penalizan el rendimiento no el uno de la la funcion de vb clasica. Seguramente los metodos de la clase de .net intentan paliar el mal rendimiento de la clase string.
    El hombre es un animal de constumbres y cuesta cambiar pero ahora sabe lo que penaliza y cada uno decida si prefiere mas rendimiento o mantener las herramientas que hasta hace poco usaba.

    Responder
  9. anonymous dice:
    13 febrero, 2009 a las 5:04 pm

    Os diré que es muy saludable para un programador de VB6 (like me) meterse a aprender C#, se eliminan costumbres un poquillo obsoletas, se aprende bien la plataforma .Net y de paso se aprende un C.

    ¿Qué más se puede pedir?

    😀 😀 😀

    (bueno, debo admitir que antes de aprender VB6 ya había pasado por C++ programando programitas para consolas, lo malo del C# es que no le gustan los punteros, son muy «unsafe»)

    D: D: D:

    Responder

Deja un comentario Cancelar respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *

← Previous Post Next Post →

Jorge Serrano

MVP Reconnect


¡Subscríbete a mi canal!
YouTube

Donaciones
Donation

Entradas recientes

  • Go – Arrays
  • Go – Operators
  • Go – Constants
  • Go – Tipos de Datos
  • Go – Variables
  • Hello Go-rld!
  • Introducción a Go o Golang
  • JSON Patch en ASP.NET Core 5 Web API
  • Null Checking en C#
  • ¿Porqué mi página web por defecto de ASP.NET Core no se vé en mi Azure Web App y me da un 404?

Categorías

  • .NET 5
  • .NET Core
  • .NET Core 3.0
  • .NET Core 3.1
  • .NET Framework 2.0
  • .NET Framework 3.0
  • .NET Framework 3.5
  • .NET Framework 4.0
  • .NET Framework 4.5
  • .NET Framework 4.6
  • .NET Framework 4.7
  • .NET Framework 4.8
  • .NET Standard 2.0
  • .NET Standard 2.1
  • AMQP
  • Android
  • Angular
  • API REST
  • Apple
  • Apple iOS
  • Apple macOs
  • Arquitectura
  • ASP.NET
  • ASP.NET Core
  • ASP.NET Core 3
  • ASP.NET Core 5
  • AWS
  • Azure App Service
  • Azure Application Insights
  • Azure Cosmos DB
  • Azure Database Migration Service
  • Azure Databricks
  • Azure DevOps
  • Azure Event Grid
  • Azure Functions
  • Azure IoT
  • Azure Portal
  • Azure PowerShell
  • Azure Queue Storage
  • Azure SQL
  • Azure Storage
  • Azure Virtual Datacenter
  • Azure WebApps
  • Big Data
  • Bing
  • Blazor
  • Blog
  • Bots
  • C#
  • C# 7.0
  • C# 7.1
  • C# 7.2
  • C# 7.3
  • C# 8.0
  • C# 9.0
  • Channel 9
  • Codeplex
  • Codespaces
  • Containers
  • Debugging
  • DevOps
  • Docker
  • Electron
  • Entity Framework
  • Entity Framework Core
  • Entity Framework Core 3.0
  • Entity Framework Core 5
  • Eventos
  • F#
  • FaaS
  • FeatureFlags
  • FeatureToggles
  • Feeds
  • Fluent Assertions
  • General
  • GIMP
  • Git
  • GitHub
  • Go
  • Google
  • Google Analytics
  • Gradle
  • gRPC
  • GSA
  • Historia de la Informática
  • HoloLens
  • HtmlAgilityPack
  • IdentityServer4
  • Inkscape
  • Ionic
  • iOS
  • IoT
  • Java
  • JavaScript
  • JDBC
  • JSON
  • Kubernetes
  • Lenguajes de Programación
  • Libros y Cursos
  • LINQ
  • Linux
  • LiteDB
  • Machine Learning
  • macOS
  • Microservices
  • Microsoft
  • Microsoft .NET Framework 4.5
  • Microsoft 365
  • Microsoft Azure
  • Microsoft Build
  • Microsoft Ignite
  • Microsoft Learn
  • Microsoft Orleans
  • Microsoft Surface Go
  • Microsoft Teams
  • ML.NET
  • MQTT
  • MRO
  • MS-DOS
  • MsCoders Madrid
  • MVP
  • NancyFx
  • Node.js
  • NoSQL
  • NuGet
  • NUnit
  • OData
  • ODP.NET Core
  • Office 2007
  • Office 2010
  • Office 2013
  • Office 2016
  • Office 2019
  • Office 365
  • Open Source
  • Open XML SDK
  • Opinión
  • Orchard CMS
  • OT
  • PaaS
  • Patterns
  • PdfSharpCore
  • Performance
  • PHP
  • Postman
  • Power BI
  • PowerShell
  • PowerShell Core
  • Productividad
  • Project Server 2019
  • R
  • Rendimiento
  • Scala
  • Scraper
  • Security
  • Serverless
  • Service Fabric
  • SharePoint Server 2019
  • SignalR
  • Sin categoría
  • Sistemas Distribuidos
  • Skype
  • Skype for Business Server 2019
  • Small Basic Online
  • SQL Server 2005
  • SQL Server 2008
  • SQL Server 2012
  • SQL Server 2014
  • SQL Server 2016
  • SQL Server 2017
  • SQL Server 2019
  • STOMP
  • Swagger
  • Testing
  • TFS 2017
  • TFS 2018
  • Tools
  • TypeScript
  • Unity
  • UWP
  • UX
  • Visio
  • Visual Basic
  • Visual Studio 2010
  • Visual Studio 2012
  • Visual Studio 2013
  • Visual Studio 2015
  • Visual Studio 2017
  • Visual Studio 2017 for Mac
  • Visual Studio 2019
  • Visual Studio 2019 for Mac
  • Visual Studio App Center
  • Visual Studio Code
  • Visual Studio IntelliCode
  • Visual Studio Live Share
  • Visual Studio Live Share Audio
  • Visual Studio Online
  • VS Anywhere
  • Vue.js
  • Web API
  • WebAssembly
  • WinDbg
  • Windows
  • Windows 10
  • Windows Compatibility Pack
  • Windows Phone 10
  • Windows Phone 7
  • Windows Phone 8
  • Windows Server 2008
  • Windows Server 2012
  • Windows Server 2016
  • Windows Server 2019
  • Windows Service
  • WinForms
  • WinUI
  • WPF
  • Xamarin
  • Xbox
  • Xcode
  • Xiaomi Mi Band 2
  • xUnit
  • YAML

Archivos

  • enero 2021
  • diciembre 2020
  • noviembre 2020
  • octubre 2020
  • septiembre 2020
  • agosto 2020
  • julio 2020
  • junio 2020
  • mayo 2020
  • abril 2020
  • marzo 2020
  • febrero 2020
  • enero 2020
  • diciembre 2019
  • noviembre 2019
  • octubre 2019
  • septiembre 2019
  • agosto 2019
  • julio 2019
  • junio 2019
  • mayo 2019
  • abril 2019
  • marzo 2019
  • febrero 2019
  • enero 2019
  • diciembre 2018
  • noviembre 2018
  • octubre 2018
  • septiembre 2018
  • agosto 2018
  • julio 2018
  • junio 2018
  • mayo 2018
  • abril 2018
  • marzo 2018
  • febrero 2018
  • enero 2018
  • diciembre 2017
  • noviembre 2017
  • octubre 2017
  • septiembre 2017
  • agosto 2017
  • julio 2017
  • junio 2017
  • febrero 2015
  • octubre 2014
  • junio 2014
  • marzo 2014
  • febrero 2014
  • enero 2014
  • diciembre 2013
  • septiembre 2013
  • agosto 2013
  • julio 2013
  • junio 2013
  • abril 2013
  • febrero 2013
  • enero 2013
  • diciembre 2012
  • noviembre 2012
  • septiembre 2012
  • agosto 2012
  • junio 2012
  • mayo 2012
  • abril 2012
  • marzo 2012
  • febrero 2012
  • enero 2012
  • diciembre 2011
  • noviembre 2011
  • octubre 2011
  • septiembre 2011
  • agosto 2011
  • julio 2011
  • junio 2011
  • mayo 2011
  • abril 2011
  • marzo 2011
  • enero 2011
  • diciembre 2010
  • noviembre 2010
  • octubre 2010
  • septiembre 2010
  • agosto 2010
  • julio 2010
  • junio 2010
  • mayo 2010
  • abril 2010
  • marzo 2010
  • febrero 2010
  • enero 2010
  • diciembre 2009
  • noviembre 2009
  • octubre 2009
  • septiembre 2009
  • agosto 2009
  • julio 2009
  • junio 2009
  • mayo 2009
  • abril 2009
  • marzo 2009
  • febrero 2009
  • enero 2009
  • diciembre 2008
  • noviembre 2008
  • octubre 2008
  • septiembre 2008
  • agosto 2008
  • julio 2008
  • junio 2008
  • mayo 2008
  • abril 2008
  • marzo 2008
  • febrero 2008
  • enero 2008
  • diciembre 2007
  • noviembre 2007
  • octubre 2007
  • septiembre 2007
  • agosto 2007
  • julio 2007
  • junio 2007
  • mayo 2007
  • abril 2007
  • marzo 2007
  • febrero 2007
  • enero 2007
  • diciembre 2006
  • noviembre 2006
  • octubre 2006
  • septiembre 2006
  • agosto 2006
  • julio 2006
  • junio 2006
  • mayo 2006
About This Site

A cras tincidunt, ut tellus et. Gravida scel ipsum sed iaculis, nunc non nam. Placerat sed phase llus, purus purus elit.

Archives Widget
  • January 2010
  • December 2009
  • November 2009
  • October 2009
Categories
  • Entertainment
  • Technology
  • Sports & Recreation
  • Jobs & Lifestyle
Search
  • twitter

Powered by WordPress  |  Business Directory by InkThemes.

This site uses cookies: Find out more.