Friday, January 27, 2012

Creating virtual machines using VBoxManage command

Please visit http://stdioe.blogspot.com/2012/01/install-vbox-with-extpack-on-ubuntu.html to read "Installing VBox with extpack on ubuntu server 11.10" article. This article is explain to installation steps of ubuntu server 11.10 and virtualbox 4.1 with screenshots and videos from zero. If you don't know or don't sure "how to" install them, that's will be helpful..



We can use VBoxManage command to create and manage a virtual machine. If we execute the VBoxManage command alone, It will get an output with all parameters and options as below:


support@tester:~$ VBoxManage
Oracle VM VirtualBox Command Line Management Interface Version 4.1.8
(C) 2005-2011 Oracle Corporation
All rights reserved.

Usage:

VBoxManage [-v|--version] print version number and exit
VBoxManage [-q|--nologo] ... suppress the logo

VBoxManage list [--long|-l] vms|runningvms|ostypes|hostdvds|hostfloppies|
bridgedifs|hostonlyifs|dhcpservers|hostinfo|
hostcpuids|hddbackends|hdds|dvds|floppies|
usbhost|usbfilters|systemproperties|extpacks

VBoxManage showvminfo <uuid>|<name> [--details]
[--machinereadable]
VBoxManage showvminfo <uuid>|<name> --log <idx>

VBoxManage registervm <filename>

VBoxManage unregistervm <uuid>|<name> [--delete]

VBoxManage createvm --name <name>
[--ostype <ostype>]
[--register]
[--basefolder <path>]
[--uuid <uuid>]

VBoxManage modifyvm <uuid|name>
[--name <name>]
[--ostype <ostype>]
[--memory <memorysize in MB>]
[--pagefusion on|off]
[--vram <vramsize in MB>]
[--acpi on|off]
[--pciattach 03:04.0]
[--pciattach 03:04.0@02:01.0]
[--pcidetach 03:04.0]
[--ioapic on|off]
[--pae on|off]
[--hpet on|off]
[--hwvirtex on|off]
[--hwvirtexexcl on|off]
[--nestedpaging on|off]
[--largepages on|off]
[--vtxvpid on|off]
[--synthcpu on|off]
[--cpuidset <leaf> <eax> <ebx> <ecx> <edx>]
[--cpuidremove <leaf>]
[--cpuidremoveall]
[--hardwareuuid <uuid>]
[--cpus <number>]
[--cpuhotplug on|off]
[--plugcpu <id>]
[--unplugcpu <id>]
[--cpuexecutioncap <1-100>]
[--rtcuseutc on|off]
[--monitorcount <number>]
[--accelerate3d on|off]
[--accelerate2dvideo on|off]
[--firmware bios|efi|efi32|efi64]
[--chipset ich9|piix3]
[--bioslogofadein on|off]
[--bioslogofadeout on|off]
[--bioslogodisplaytime <msec>]
[--bioslogoimagepath <imagepath>]
[--biosbootmenu disabled|menuonly|messageandmenu]
[--biossystemtimeoffset <msec>]
[--biospxedebug on|off]
[--boot<1-4> none|floppy|dvd|disk|net>]
[--nic<1-N> none|null|nat|bridged|intnet|hostonly|
generic]
[--nictype<1-N> Am79C970A|Am79C973|
82540EM|82543GC|82545EM|
virtio]
[--cableconnected<1-N> on|off]
[--nictrace<1-N> on|off]
[--nictracefile<1-N> <filename>]
[--nicproperty<1-N> name=[value]]
[--nicspeed<1-N> <kbps>]
[--nicbootprio<1-N> <priority>]
[--nicpromisc<1-N> deny|allow-vms|allow-all]
[--nicbandwidthgroup<1-N> none|<name>]
[--bridgeadapter<1-N> none|<devicename>]
[--hostonlyadapter<1-N> none|<devicename>]
[--intnet<1-N> <network name>]
[--natnet<1-N> <network>|default]
[--nicgenericdrv<1-N> <driver>
[--natsettings<1-N> [<mtu>],[<socksnd>],
[<sockrcv>],[<tcpsnd>],
[<tcprcv>]]
[--natpf<1-N> [<rulename>],tcp|udp,[<hostip>],
<hostport>,[<guestip>],<guestport>]
[--natpf<1-N> delete <rulename>]
[--nattftpprefix<1-N> <prefix>]
[--nattftpfile<1-N> <file>]
[--nattftpserver<1-N> <ip>]
[--natbindip<1-N> <ip>
[--natdnspassdomain<1-N> on|off]
[--natdnsproxy<1-N> on|off]
[--natdnshostresolver<1-N> on|off]
[--nataliasmode<1-N> default|[log],[proxyonly],
[sameports]]
[--macaddress<1-N> auto|<mac>]
[--mouse ps2|usb|usbtablet
[--keyboard ps2|usb
[--uart<1-N> off|<I/O base> <IRQ>]
[--uartmode<1-N> disconnected|
server <pipe>|
client <pipe>|
file <file>|
<devicename>]
[--guestmemoryballoon <balloonsize in MB>]
[--gueststatisticsinterval <seconds>]
[--audio none|null|oss|alsa|pulse]
[--audiocontroller ac97|hda|sb16]
[--clipboard disabled|hosttoguest|guesttohost|
bidirectional]
[--vrde on|off]
[--vrdeextpack default|<name>
[--vrdeproperty <name=[value]>]
[--vrdeport <hostport>]
[--vrdeaddress <hostip>]
[--vrdeauthtype null|external|guest]
[--vrdeauthlibrary default|<name>
[--vrdemulticon on|off]
[--vrdereusecon on|off]
[--vrdevideochannel on|off]
[--vrdevideochannelquality <percent>]
[--usb on|off]
[--usbehci on|off]
[--snapshotfolder default|<path>]
[--teleporter on|off]
[--teleporterport <port>]
[--teleporteraddress <address|empty>
[--teleporterpassword <password>]

VBoxManage clonevm <uuid>|<name>
[--snapshot <uuid>|<name>]
[--mode machine|machineandchildren|all]
[--options link|keepallmacs|keepnatmacs|
keepdisknames]
[--name <name>]
[--basefolder <basefolder>]
[--uuid <uuid>]
[--register]

VBoxManage import <ovf/ova>
[--dry-run|-n]
[--options keepallmacs|keepnatmacs]
[more options]
(run with -n to have options displayed
for a particular OVF)

VBoxManage export <machines> --output|-o <ovf/ova>
[--legacy09]
[--manifest]
[--vsys <number of virtual system>]
[--product <product name>]
[--producturl <product url>]
[--vendor <vendor name>]
[--vendorurl <vendor url>]
[--version <version info>]
[--eula <license text>]
[--eulafile <filename>]

VBoxManage startvm <uuid>|<name>...
[--type gui|sdl|headless]

VBoxManage controlvm <uuid>|<name>
pause|resume|reset|poweroff|savestate|
acpipowerbutton|acpisleepbutton|
keyboardputscancode <hex> [<hex> ...]|
setlinkstate<1-N> on|off |
nic<1-N> null|nat|bridged|intnet|hostonly|generic
[<devicename>] |
nictrace<1-N> on|off
nictracefile<1-N> <filename>
nicproperty<1-N> name=[value]
natpf<1-N> [<rulename>],tcp|udp,[<hostip>],
<hostport>,[<guestip>],<guestport>
natpf<1-N> delete <rulename>
guestmemoryballoon <balloonsize in MB>]
gueststatisticsinterval <seconds>]
usbattach <uuid>|<address> |
usbdetach <uuid>|<address> |
vrde on|off |
vrdeport <port> |
vrdeproperty <name=[value]> |
vrdevideochannelquality <percent>
setvideomodehint <xres> <yres> <bpp> [display] |
screenshotpng <file> [display] |
setcredentials <username> <password> <domain>
[--allowlocallogon <yes|no>] |
teleport --host <name> --port <port>
[--maxdowntime <msec>] [--password password]
plugcpu <id>
unplugcpu <id>
cpuexecutioncap <1-100>

VBoxManage discardstate <uuid>|<name>

VBoxManage adoptstate <uuid>|<name> <state_file>

VBoxManage snapshot <uuid>|<name>
take <name> [--description <desc>] [--pause] |
delete <uuid>|<name> |
restore <uuid>|<name> |
restorecurrent |
edit <uuid>|<name>|--current
[--name <name>]
[--description <desc>] |
list [--details|--machinereadable]
showvminfo <uuid>|<name>

VBoxManage closemedium disk|dvd|floppy <uuid>|<filename>
[--delete]

VBoxManage storageattach <uuid|vmname>
--storagectl <name>
[--port <number>]
[--device <number>]
[--type dvddrive|hdd|fdd]
[--medium none|emptydrive|
<uuid>|<filename>|host:<drive>|iscsi]
[--mtype normal|writethrough|immutable|shareable|
readonly|multiattach]
[--comment <text>]
[--setuuid <uuid>]
[--setparentuuid <uuid>]
[--passthrough on|off]
[--tempeject on|off]
[--nonrotational on|off]
[--bandwidthgroup <name>]
[--forceunmount]
[--server <name>|<ip>]
[--target <target>]
[--tport <port>]
[--lun <lun>]
[--encodedlun <lun>]
[--username <username>]
[--password <password>]
[--intnet]

VBoxManage storagectl <uuid|vmname>
--name <name>
[--add ide|sata|scsi|floppy|sas]
[--controller LSILogic|LSILogicSAS|BusLogic|
IntelAHCI|PIIX3|PIIX4|ICH6|I82078]
[--sataideemulation<1-4> <1-30>]
[--sataportcount <1-30>]
[--hostiocache on|off]
[--bootable on|off]
[--remove]

VBoxManage bandwidthctl <uuid|vmname>
--name <name>
[--add disk|network]
[--limit <megabytes per second>
[--delete]

VBoxManage showhdinfo <uuid>|<filename>

VBoxManage createhd --filename <filename>
--size <megabytes>|--sizebyte <bytes>
[--format VDI|VMDK|VHD] (default: VDI)
[--variant Standard,Fixed,Split2G,Stream,ESX]

VBoxManage modifyhd <uuid>|<filename>
[--type normal|writethrough|immutable|shareable|
readonly|multiattach]
[--autoreset on|off]
[--compact]
[--resize <megabytes>|--resizebyte <bytes>]

VBoxManage clonehd <uuid>|<filename> <uuid>|<outputfile>
[--format VDI|VMDK|VHD|RAW|<other>]
[--variant Standard,Fixed,Split2G,Stream,ESX]
[--existing]

VBoxManage convertfromraw <filename> <outputfile>
[--format VDI|VMDK|VHD]
[--variant Standard,Fixed,Split2G,Stream,ESX]
[--uuid <uuid>
VBoxManage convertfromraw stdin <outputfile> <bytes>
[--format VDI|VMDK|VHD]
[--variant Standard,Fixed,Split2G,Stream,ESX]
[--uuid <uuid>

VBoxManage getextradata global|<uuid>|<name>
<key>|enumerate

VBoxManage setextradata global|<uuid>|<name>
<key>
[<value>] (no value deletes key)

VBoxManage setproperty machinefolder default|<folder> |
vrdeauthlibrary default|<library> |
websrvauthlibrary default|null|<library> |
vrdeextpack null|<library> |
loghistorycount <value>

VBoxManage usbfilter add <index,0-N>
--target <uuid>|<name>|global
--name <string>
--action ignore|hold (global filters only)
[--active yes|no] (yes)
[--vendorid <XXXX>] (null)
[--productid <XXXX>] (null)
[--revision <IIFF>] (null)
[--manufacturer <string>] (null)
[--product <string>] (null)
[--remote yes|no] (null, VM filters only)
[--serialnumber <string>] (null)
[--maskedinterfaces <XXXXXXXX>]

VBoxManage usbfilter modify <index,0-N>
--target <uuid>|<name>|global
[--name <string>]
[--action ignore|hold] (global filters only)
[--active yes|no]
[--vendorid <XXXX>|""]
[--productid <XXXX>|""]
[--revision <IIFF>|""]
[--manufacturer <string>|""]
[--product <string>|""]
[--remote yes|no] (null, VM filters only)
[--serialnumber <string>|""]
[--maskedinterfaces <XXXXXXXX>]

VBoxManage usbfilter remove <index,0-N>
--target <uuid>|<name>|global

VBoxManage sharedfolder add <vmname>|<uuid>
--name <name> --hostpath <hostpath>
[--transient] [--readonly] [--automount]

VBoxManage sharedfolder remove <vmname>|<uuid>
--name <name> [--transient]

VBoxManage guestproperty get <vmname>|<uuid>
<property> [--verbose]

VBoxManage guestproperty set <vmname>|<uuid>
<property> [<value> [--flags <flags>]]

VBoxManage guestproperty enumerate <vmname>|<uuid>
[--patterns <patterns>]

VBoxManage guestproperty wait <vmname>|<uuid> <patterns>
[--timeout <msec>] [--fail-on-timeout]

VBoxManage guestcontrol <vmname>|<uuid>
exec[ute]
--image <path to program>
--username <name> --password <password>
[--dos2unix]
[--environment "<NAME>=<VALUE> [<NAME>=<VALUE>]"]
[--timeout <msec>] [--unix2dos] [--verbose]
[--wait-exit] [--wait-stdout] [--wait-stderr]
[-- [<argument1>] ... [<argumentN>]]

copyfrom
<source on guest> <destination on host>
--username <name> --password <password>
[--dryrun] [--follow] [--recursive] [--verbose]

copyto|cp
<source on host> <destination on guest>
--username <name> --password <password>
[--dryrun] [--follow] [--recursive] [--verbose]

createdir[ectory]|mkdir|md
<director[y|ies] to create on guest>
--username <name> --password <password>
[--parents] [--mode <mode>] [--verbose]

stat
<file element(s) to check on guest>
--username <name> --password <password>
[--verbose]

updateadditions
[--source <guest additions .ISO>] [--verbose]

VBoxManage debugvm <uuid>|<name>
dumpguestcore --filename <name> |
info <item> [args] |
injectnmi |
log [--release|--debug] <settings> ...|
logdest [--release|--debug] <settings> ...|
logflags [--release|--debug] <settings> ...|
osdetect |
osinfo |
getregisters [--cpu <id>] <reg>|all ... |
setregisters [--cpu <id>] <reg>=<value> ... |
statistics [--reset] [--pattern <pattern>]
[--descriptions]

VBoxManage metrics list [*|host|<vmname> [<metric_list>]]
(comma-separated)

VBoxManage metrics setup
[--period <seconds>] (default: 1)
[--samples <count>] (default: 1)
[--list]
[*|host|<vmname> [<metric_list>]]

VBoxManage metrics query [*|host|<vmname> [<metric_list>]]

VBoxManage metrics enable
[--list]
[*|host|<vmname> [<metric_list>]]

VBoxManage metrics disable
[--list]
[*|host|<vmname> [<metric_list>]]

VBoxManage metrics collect
[--period <seconds>] (default: 1)
[--samples <count>] (default: 1)
[--list]
[--detach]
[*|host|<vmname> [<metric_list>]]

VBoxManage hostonlyif ipconfig <name>
[--dhcp |
--ip<ipv4> [--netmask<ipv4> (def: 255.255.255.0)] |
--ipv6<ipv6> [--netmasklengthv6<length> (def: 64)]]
create |
remove <name>

VBoxManage dhcpserver add|modify --netname <network_name> |
--ifname <hostonly_if_name>
[--ip <ip_address>
--netmask <network_mask>
--lowerip <lower_ip>
--upperip <upper_ip>]
[--enable | --disable]

VBoxManage dhcpserver remove --netname <network_name> |
--ifname <hostonly_if_name>

VBoxManage extpack install [--replace] <tarball> |
uninstall [--force] <name> |
cleanup

Let's create a sample virtual machine:

1-) The first step is the VM creation, (We are using a "Ubuntu OS + VBox" system that is installed in "http://stdioe.blogspot.com/2012/01/install-vbox-with-extpack-on-ubuntu.html" article. It is recommanded to read that article first.)


support@tester:~$ VBoxManage createvm --name testMachine --ostype Debian --register
Virtual machine 'testMachine' is created and registered.UUID: e2bfd530-14fb-4b8e-8dc2-8523c9bd045e
Settings file: '/home/support/VirtualBox VMs/testMachine/testMachine.vbox'
support@tester:~$

2-) At this point, we can start with checking existing Virtual machine with following command:

support@tester:~$ VBoxManage showvminfo testMachine

Actually, our virtual machine has just been created but It hasn't got any hard drives and some of those settings may not required. For example, the existing virtual machine memory size is 128 megabytes. Probably you want to increase it. You may not want to use NAT mode ethernet device. Right now, let's change some options on our virtual sample.

3-) Change memory and then check it:


support@tester:~$ VBoxManage modifyvm testMachine --memory 256
support@tester:~$
support@tester:~$ VBoxManage showvminfo testMachine | grep "Memory size"
Memory size: 256MB

4-) Change nic (ethernet interface) bridge mode. We need a bridge adapter for this and the bridge adapter needs a physical interface on base OS. I am checking the pysical interface on base OS:

support@tester:~$ ifconfig
eth0 Link encap:Ethernet HWaddr 00:1a:64:5b:60:2c
inet addr:172.28.202.216 Bcast:172.28.202.255 Mask:255.255.255.0
inet6 addr: fe80::21a:64ff:fe5b:602c/64 Scope:Link
UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1
RX packets:2932762 errors:0 dropped:0 overruns:0 frame:0
TX packets:1149518 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:1000
RX bytes:936032419 (936.0 MB) TX bytes:89178513 (89.1 MB)
Interrupt:17 Memory:da000000-da012800

And I learned that my physical interface's name is "eth0". Right now, I can create a bridge adapter and check with these commands:

support@tester:~$ VBoxManage modifyvm testMachine --bridgeadapter1 eth0
support@tester:~$ VBoxManage modifyvm testMachine --nic1 bridged
support@tester:~$ VBoxManage showvminfo testMachine | grep "NIC 1"
NIC 1: MAC: 080027E31FFE, Attachment: Bridged Interface 'eth0', Cable connected: on, Trace: off (file: none), Type: 82540EM, Reported speed: 0 Mbps, Boot priority: 0, Promisc Policy: deny
support@tester:~$


5-) Create an HDD and attach to virtual machine using following commands:


support@tester:~$ VBoxManage createhd --filename testMachine.vdi --size 18000 --format
VDI0%...10%...20%...30%...40%...50%...60%...70%...80%...90%...100%
Disk image created. UUID: 970c500d-2476-44ef-b11b-5938b5150c91
support@tester:~$ VBoxManage storagectl testMachine --name "SATA Controller" --add sata --controller IntelAhci
support@tester:~$ VBoxManage storageattach "testMachine" --storagectl "SATA Controller" --port 0 --device 0 --type hdd --medium testMachine.vdi

and you can find the related information in "VBoxManage showvminfo testMachine" command output:


support@tester:~$
VBoxManage showvminfo testMachine
......
Storage Controller Name (0): SATA Controller
Storage Controller Type (0): IntelAhci
Storage Controller Instance Number (0): 0
Storage Controller Max Port Count (0): 30
Storage Controller Port Count (0): 30
Storage Controller Bootable (0): on
SATA Controller (0, 0): /home/support/testMachine.vdi (UUID: 970c500d-2476-44ef-b11b-5938b5150c91)
......

Also you can change some of those options on HDD specifications and controller type and all of them. For example, you can select IDE for SATA in my sample. Or size of disk or disk format (VDI, VMDK, VHD) etc.

If you need, you can use "VBoxManage createhd", "VBoxManage modifyhd" or "VBoxManage clonehd" to create a new one, modify the existing one or create a copy of existing one...

6-) We need to mount a cdrom or dvd to our virtual machine to start operation system installation. The following command will download a dvd image from the debian site and do that mounting progress:

support@tester:~$ wget http://cdimage.debian.org/debian-cd/6.0.3/amd64/iso-cd/debian-6.0.3-amd64-netinst.iso
support@tester:~$ VBoxManage storagectl testMachine --name "IDE Controller" --add ide --controller PIIX4
support@tester:~$ VBoxManage storageattach testMachine --storagectl "IDE Controller" --port 1 --device 0 --type dvddrive --medium debian-6.0.3-amd64-i386-netinst.iso
When we execute 'VBoxManage showvminfo testMachine | grep "IDE Controller" ' command to check the last step, we should see following output:

support@tester:~$ VBoxManage showvminfo testMachine | grep "IDE Controller"
Storage Controller Name (1): IDE Controller
IDE Controller (1, 0): /home/support/debian-6.0.3-amd64-i386-netinst.iso (UUID: cbc77834-7434-4a3c-af96-858ae1af1731)
support@tester:~$



7-) Almost all mandatory steps are completed, except "remote display" one. We haven't got any GUI and we need a monitor to watch virtual machine output! We can use following first command to enable remote display feature and the second command to check the vrde option on our virtual machine.

support@tester:~$ VBoxManage modifyvm testMachine --vrde on
support@tester:~$ VBoxManage showvminfo testMachine | grep VRDE
VRDE: enabled (Address 0.0.0.0, Ports 3389, MultiConn: off, ReuseSingleConn: off, Authentication type: null)
VRDE property: TCP/Ports = "3389"
VRDE property: TCP/Address = <not set>
VRDE property: VideoChannel/Enabled = <not set>
VRDE property: VideoChannel/Quality = <not set>
VRDE property: VideoChannel/Downscale Protection = <not set>
VRDE property: Client/DisableDisplay = <not set>
VRDE property: Client/DisableInput = <not set>
VRDE property: Client/DisableAudio = <not set>
VRDE property: Client/DisableUSB = <not set>
VRDE property: Client/DisableClipboard = <not set>
VRDE property: Client/DisableUpstreamAudio = <not set>
VRDE property: H3DRedirect/Enabled = <not set>
VRDE property: Security/Method = <not set>
VRDE property: Security/ServerCertificate = <not set>
VRDE property: Security/ServerPrivateKey = <not set>
VRDE property: Security/CACertificate = <not set>
VRDE Connection: not activesupport@tester:~$

We can boot testMachine but we have only one session right on VRDE. If we connect to virtual machine remote display from more than one clients, we have to change MultiConn option to "on". Also, if the port 3389 is used by another process we have to change it. Let's change the port and the multiConn option and then check it again,

support@tester:~$ VBoxManage modifyvm testMachine --vrdemulticon on --vrdeport 3390
support@tester:~$ VBoxManage showvminfo testMachine | grep VRDE
VRDE: enabled (Address 0.0.0.0, Ports 3390, MultiConn: on, ReuseSingleConn: off, Authentication type: null)
VRDE property: TCP/Ports = "3390"
VRDE property: TCP/Address = <not set>
VRDE property: VideoChannel/Enabled = <not set>
VRDE property: VideoChannel/Quality = <not set>
VRDE property: VideoChannel/DownscaleProtection = <not set>
VRDE property: Client/DisableDisplay = <not set>
VRDE property: Client/DisableInput = <not set>
VRDE property: Client/DisableAudio = <not set>
VRDE property: Client/DisableUSB = <not set>
VRDE property: Client/DisableClipboard = <not set>
VRDE property: Client/DisableUpstreamAudio = <not set>
VRDE property: H3DRedirect/Enabled = <not set>
VRDE property: Security/Method = <not set>
VRDE property: Security/ServerCertificate = <not set>
VRDE property: Security/ServerPrivateKey = <not set>
VRDE property: Security/CACertificate = <not set>
VRDE Connection: not activesupport@tester:~$

8-) Well. Our Virtual Machine is really ready to boot right now. Let's boot it.

support@tester:~$ VBoxHeadless --startvm testMachine
Oracle VM VirtualBox Headless Interface 4.1.8(C) 2008-2011 Oracle Corporation
All rights reserved.

VRDE server is listening on port 3390.

This command does not release the treminal and if we close terminal window or press "ctrl+c", the virtual machine will be aborted. We will come back to this boot issue again.

9-) Connect to virtual machine via RDP client:

ismail@ismail-ThinkPad-T410:~$ rdesktop 172.28.202.216:3390
Autoselected keyboard map en-usWARNING: Remote desktop changed from 800x600 to 640x480.

and you can see something like this :


Ok. Everything is well. But we want to auto start this virtual machine when booting the base operating system that is an Ubuntu server 11.10. In this case we have to write a start-up shell script and apply with updare-rc.d to inittab.

10-) The most important step of writing the start-up shell script is to set the right ownership. Because, we did everything as support user. But root user will execute it, when the base operation system is booting.

#!/bin/bash

u=`/usr/bin/id -u`

case "$1" in
start)
if [ $u -eq 0 ]; then
/bin/su support -c '/usr/bin/VBoxHeadless --startvm prxySMS &'
else
/usr/bin/VBoxHeadless -startvm testMachine &
fi
;;
stop)
# something for shutdown virtual machine via vm OS, somehow ..
;;
restart)
# commands for restarting will come here then...hah?
stop
start
;;
status)
# May be shown running process with ps command with "| grep VBoxHeadless"
;;
*)
echo "Usage: /etc/init.d/prxySMS_starter :) [start|stop|restart|status]"
exit 1
;;
esac
exit 0

This file is recorded with the filename "testMachine_starter" in folder /etc/init.d. We give the execution permission using "chmod +x /etc/init.d/testMachine_starter". Now, we have to add it to startup with update-rc.d command like this,

ismail@ismail-ThinkPad-T410:~$  update-rc.d testMachine_starter defaults 95

I put a "95" option in command shown below because I want to start the virtual machine after others. This number part is not necessary.

Wednesday, January 25, 2012

Installing VBox with extpack on ubuntu server 11.10



This article is about Virtual Box installation and virtual machine / virtual operation system installation WITHOUT a Graphical User Interface (GUI). I'm using an IBM Blade hardware for this Installation sample. Some information for this hardware is shown in pictures below:


The IBM Blade Chassis Hardware Topology Inventory details


The IBM Blade Server that located in the IBM Blade Chassis

I want to describe hardware details and base operating system before virtual system because, this may affect virtual parts. Actually this risc is really very low for VirtualBox versus OpenVZ. Because there are criterias of hardware compatibility for other virtualization products. I'm going to use a Ubuntu Server 11.10 for base operation system so this OS is used by most of the people. Also I'm going to select a 64 bit operation system to able to use 64 bit virtual systems.

Mount iso image, and check KVM and media tray and power on as show in following movie.



Ubuntu 11.10 Server AMD 64 bit OS installation steps are shown in following pictures: (These pictures show the steps that are almost all in default. You may want to jump if you wish.)











VirtualBox Installation;

1-) Add one of the following lines according to your Ubuntu server to your /etc/apt/sources.list

deb http://download.virtualbox.org/virtualbox/debian oneiric contrib
deb http://download.virtualbox.org/virtualbox/debian natty contrib
deb http://download.virtualbox.org/virtualbox/debian maverick contrib non-free
deb http://download.virtualbox.org/virtualbox/debian lucid contrib non-free
deb http://download.virtualbox.org/virtualbox/debian karmic contrib non-free
deb http://download.virtualbox.org/virtualbox/debian hardy contrib non-free
deb http://download.virtualbox.org/virtualbox/debian squeeze contrib non-free
deb http://download.virtualbox.org/virtualbox/debian lenny contrib non-free

Actually I need adding only the first line for my OS because, my ubuntu distribution is Oneiric. But your distribution may have a different version, so I write other distributions.

2-) Downloading the Oracle public key for apt-secure and registering:

support@tester:~$ wget http://download.virtualbox.org/virtualbox/debian/oracle_vbox.asc
support@tester:~$ sudo apt-key add oracle_vbox.asc

or

support@tester:~$ wget -q http://download.virtualbox.org/virtualbox/debian/oracle_vbox.asc -O- | sudo apt-key add -

3-) Installing virtualbox-4.1:

support@tester:~$ sudo apt-get update
support@tester:~$ sudo apt-get install virtualbox-4.1

4-) Downloading extension pack:

support@tester:~$ wget http://download.virtualbox.org/virtualbox/4.1.8/Oracle_VM_VirtualBox_Extension_Pack-4.1.8-75467.vbox-extpack

5-) Installing the extension pack for Oracle VirtualBox. If we don't install extension pack, we won't be able to use remote display features. So our system hasn't got GUI yet, we can not start to install virtual system without extension pack. To install extension pack,

support@tester:~$ VBoxManage extpack install Oracle_VM_VirtualBox_Extension_Pack-4.1.8-75467.vbox-extpack

You can find all of the official instructions and installation packages in https://www.virtualbox.org/wiki/Downloads .

You can watch these instructions on following movie:



You can visit http://stdioe.blogspot.com/2012/01/creating-virtual-machine-with.html to read "Creating virtual machines using VBoxManage command" article. It is the next step of this article.

Wednesday, January 18, 2012

When to use Java Native Interface (JNI) ?

Programming in Java is totally fun, especially, if you use it for general purposes. The term 'general purposes" is stated here as "the program that needs file, socket, web, gui operations" opposite to a special problem. That is, a special problem may be a scientific one which requires loops, array operations and basic operations. A program like this can be easily written in other languages.

Sometimes, we need other libraries which are not yet implemented for Java or some operations that perform some low level operations which are not handled by the JVM. For instance, a library written in C can not be directly used in Java. You have to either re-write it in Java or use the Java Native Interface (JNI).

But there is something worth to talk about. People generally think that a native function that called from Java must run faster than in Java. But it is not true. Yes, a native function (we use the term native for compiled codes) may run faster and via versa. The important point here is that Java can not directly perform a function call directly, that is, there is some preparation process needed.

To be clear, let me give an example. Suppose that we have a C++ function 'mean' which stands for calculating the arithmetic mean of a double array. We have also a function 'jmean' which is written in Java for the same purpose. Now, suppose that we have a double array with size of 1,000,000 and has values from 0.0 to 999,999.
The processes of passing this array reference to C++ and getting the calculated result costs 112 milliseconds. When I tried the same test for the function written in Java, I got the result of 10-12 milliseconds. It seems there is a significant performance difference between them!

In this example, the biggest amount of time is consumed by the calling preparation, not the calculation mean itself.

We can summarize those results as :
1) Calling a native method for millions times makes a significant performance loss.
2) Use JNI if you have to. Maybe, if it is performing a low level operation or converting the C code to Java is hard. For example accessing to LPT port is not possible in Java and you need to use JNI here.

and I can personally say that:
"An increase on performance depends on the job performed by the native method."

Finally, the old book, Essential JNI - Java Native Interface is a good book if you really interested in JNI. JNI is generally used for calling C/C++ functions from Java and accessing Java objects from C/C++. JNI also stands for "creating JVM's in C/C++" code and that means you can manipulate java programs as acting like the JVM itself.

JNI is in everyday Java life. JCurses library uses JNI for coloured console for the people who got bored using System.out.println. QJambi uses JNI for constructing a bridge between Java and Qt classes. Java's standard libraries such as AWT also bridges between native GUI API's and Java. Charva uses JNI for GUI'd text terminals. And, of cource, there are lots of examples on this.



Friday, January 6, 2012

Lets implement a simple Lisp Interpreter in Java

Edit 2015.03.20 : If you are really interested in implementing a LISP like language in Java, you can visit this, this and this

You are probably programing with C++, Java or .Net thingies but not Lisp. Why? Because it is the most beautiful language that human ever made :) Let me explain.

If you write in a programming language, you have to look and understand the interpreter's or compiler's principals. If you didn't do that yet, let me say, when you look inside an interpreter you will see a picture in which hundreds of objects being copied from one data structure to another called stacks. When you trace the interpreter, you will see nothing except those abstract data structures. The scene you will see is like a casino with hundreds of card dealers...

But when you program in Lisp, the interpreter exactly does what you write. There is no abstraction, no hacking. You will deal the cards in your fully controlled casino. Having knowledge about what the interpreter does is everything.

Lets look at the following Lisp expression

(+ 2 (+ 3 2))

which states that interpreter first will sum 2 and 3 and the gained number will be summed with 2. The result should be 7. How did we do that? Because of our primary school skills. Lets do that with a stupid machine that can only handle basic stack operations as in assembly language.

Suppose that we have a stack object and we are sequentially adding tokens into that stack. A token is defined as an atomic element of this expression. So our tokens are (, +, 2, (, +, 3, 2, ) and ) , respectively.

Now, take the first token and put it into the stack. Our stack is like that:


/


Lets add more elements until we encounter a closing parenthesis.


(+2(+32)

Again, suppose that, whenever we encounter a closing parenthesis, we collect some elements from the stack until we get an opening parenthesis, say that, we have now


(+32)

collected from the stack. Calculate this simple expression and put the result back to our stack. Since result of the sub expression (+ 3 2) is 5, our stack comes to shape of


(+25

We didn't finish reading the tokens yet. We have one more token to push into the stack.


(+25)

We encounter a closing parenthesis again and that means we have to handle the sub expression and put back the result to the stack. Since there is no sub expressions, we have the root expression at hand. Reading until having an opening parenthesis and performing calculations will give the result of 7 after all.

Note that, all we did here spans a 50 lines of Java class. I hope taking a glance at this code will help you to capture the whole story.



package smalllisp;

import java.util.Stack;

public class SmallLisp {

  Stack<String> stack;
  
  public SmallLisp(){
    String[] tokens = new String[]{"(","+","2","(","+","3","2",")",")"};
    stack = new Stack<String>();
    for (int i=0;i<tokens.length;i++){
      stack.push(tokens[i]);
      if(tokens[i].equals(")")) Interprete(); 
    }
  }
  
  public void Interprete(){
    String tok;
    Stack<String> callStack = new Stack<String>();
    tok = stack.pop(); /* This is the ) character */
    while(!(tok=stack.pop()).equals("(")){
      callStack.push(tok);
    }
    Call(callStack);
  }
  
  public void Call(Stack<String> callStack){
    String func = callStack.pop(); /* This is the operator or function */
    if(func.equals("+")) {
      double result = Plus(callStack);
      stack.push(String.valueOf(result));
    }
    //if(func.equals("-")) Minus(callStack);
  }
  
  public double Plus(Stack<String> callStack){
    double a = Double.parseDouble(callStack.pop());
    double b = Double.parseDouble(callStack.pop());
    System.out.println("Answer is "+(a+b));
    return(a+b);
  } 
  
  public static void main(String[] args) {
    new SmallLisp();
  }
}


Todo:
  • Implement the minus function yourself.
  • Implement the product function yourself.
Well done !

A Simple Qt Application Example using Qt Creator

Well, you are programming with C++ and you want to expand your programs with GUI components, Windows, Sockets, Threads, Timers and Processes. Since the standard C++ library does not include classes for those stuff, any C++ program needs external packages to cope with real world problems.

It is almost always a problem to find external libraries that provide platform independency. Java solves this problem with its standard API library which includes classes for threading, file operations, GUI stuff and networking. Qt does nearly the same thing. So, if you want to develop a program using a single framework, Qt is a good choice.

Although programming with Qt make people feel like programming in Java or any other "comfortable" language, do not forget that it is still C++. That means, you can be more relax in memory management but you are still face to face with the machine with your compiled code.

Qt is similar to Java as it is platform independent, that is, you will compile your source code in Windows, Linux and Mac and you will see the same running beautiful program.

If you are familiar with the Qt and you are seeking a framework to use in your C++ project, do not think any more and use it! And stop to read the remaining part of this text. If you don't know how to use it, follow the simplest Qt example in the world... Then have a Qt book and read it. You will feel comfortable with it after a month or two if you have ever programmed with Java or C++.

Yes, let's create a project. Download the Qt Creator from http://qt.nokia.com/products/ and install it. I suppose that you know how to install programs in your operating system. After a big installation progress, run the Qt Creator. You will see a window similar to this:


Then follow the menu "File >> New File or Project" and click it. A new window will be opened:


Select "Qt Widget Project >> Qt Gui Application" using the window then press "Choose".


Give a name for your project.



Select "Desktop" and click next.


Leave the class information as is and click next. When you learn how to program with Qt, you will need more than more window elements but a single one enough for our simple example.


Finally, we have a project which is ready to run. Unfortunately, it does nothing except showing an empty window. See your running empty form by typing CTRL + R key combination or click the menu "Build >> Run".


The panel on the left side shows our project configuration, .h (header), .cpp (C++ source) and gui (forms) files. You can simply activate by clicking on them. Lets click the "Forms >> mainwindow.ui" on the left side panel. 

Now, it seems our empty form is ready for designing. The left side panel now shows other GUI components which can be dragged and dropped on the empty form. Now find the Line Edit component under the "Input Widgets" group and drag & drop to the empty form. You can change its dimensions, name and other properties using the right side panels. But, leave it as is and find the push button component and create one on the form. 

We have now a filled form with a single textbox and a button. Since there is no action defined, when you run your program with the CTRL + R combination, you will see your form but push button does nothing when you click on it. Lets write something on the "text edit" when the push button is clicked. For those, we will add a code to mainwindow.h file. Select the mainwindow.h file and edit it like the following screenshot.


We added the code 

private slots:
    void pushbutton1_click();



in file mainwindow.h so we are able to define an action for the click event of the push button. Not that pushbutton1_click() is a function name which can be also selected as anything else. In Qt, we are controlling the user actions using a signaling mechanism. Every signal sender in Qt, defines SIGNAL 's. A signal catcher must define a SLOT for this. We want our code to catch the "clicking" signals from the push putton, so we defined a slot.

Now, select the mainwindow.cpp, which is the source code of our project and implement the function "pushbutton1_click()" which is defined in the corresponding header file.



void MainWindow::pushbutton1_click(){
    this->ui->lineEdit->setText("Qt Signals are easy");
}

We implemented the pushbutton1_click() in cpp file, which are defined in header file before. Now, we are quite ready because our program will put a "Qt Signals are easy" message on the this->ui->lineEdit object. Note that, lineEdit is the default name for this object and it is changeable by the user. Finally, we have to "link" the button's click action to MainWindow::pushbutton1_click() method. For that, edit the 



MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)
{
    ui->setupUi(this);
}

to 

MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)
{
    ui->setupUi(this);
    this->connect(this->ui->pushButton, SIGNAL(clicked()), this, SLOT(pushbutton1_click()));
}

So we have just connected the pushbutton's "clicked" signal to our pushbutton1_click() slot. That's all. Run the program.



After the compiling and running progress, click the push button and see the message on the text box.


SIGNAL  and SLOT mechanism is the most important thing in the Qt world to learn! Follow these steps to learn much:


  • Put a progress bar on the form. When we clicked to pushbutton, let the progressbar to show value of 50%
  • Create another pushbutton. When somebody clicks to pushbutton, show a message box containing a "Hello world!" text
  • Create a timer. Set the interval of timer to 1000 milliseconds (1 second). In each time the timer activated, show how many times the timer activated on the text box.
Read more books and tutorials and code something is not really meaningful. Qt is really easy to learn, especially, if you learned the SIGNAL & SLOT mechanism.

Good luck in your Qt life!