Background: #fff
Foreground: #000
PrimaryPale: #8cf
PrimaryLight: #18f
PrimaryMid: #04b
PrimaryDark: #014
SecondaryPale: #ffc
SecondaryLight: #fe8
SecondaryMid: #db4
SecondaryDark: #841
TertiaryPale: #eee
TertiaryLight: #ccc
TertiaryMid: #999
TertiaryDark: #666
Error: #f88
<!--{{{-->
<div class='toolbar' macro='toolbar [[ToolbarCommands::EditToolbar]]'></div>
<div class='title' macro='view title'></div>
<div class='editor' macro='edit title'></div>
<div macro='annotations'></div>
<div class='editor' macro='edit text'></div>
<div class='editor' macro='edit tags'></div><div class='editorFooter'><span macro='message views.editor.tagPrompt'></span><span macro='tagChooser excludeLists'></span></div>
<!--}}}-->
To get started with this blank [[TiddlyWiki]], you'll need to modify the following tiddlers:
* [[SiteTitle]] & [[SiteSubtitle]]: The title and subtitle of the site, as shown above (after saving, they will also appear in the browser title bar)
* [[MainMenu]]: The menu (usually on the left)
* [[DefaultTiddlers]]: Contains the names of the tiddlers that you want to appear when the TiddlyWiki is opened
You'll also need to enter your username for signing your edits: <<option txtUserName>>
<<importTiddlers>>
<!--{{{-->
<link rel='alternate' type='application/rss+xml' title='RSS' href='index.xml' />
<!--}}}-->
These [[InterfaceOptions]] for customising [[TiddlyWiki]] are saved in your browser

Your username for signing your edits. Write it as a [[WikiWord]] (eg [[JoeBloggs]])

<<option txtUserName>>
<<option chkSaveBackups>> [[SaveBackups]]
<<option chkAutoSave>> [[AutoSave]]
<<option chkRegExpSearch>> [[RegExpSearch]]
<<option chkCaseSensitiveSearch>> [[CaseSensitiveSearch]]
<<option chkAnimate>> [[EnableAnimations]]

----
Also see [[AdvancedOptions]]
<!--{{{-->
<div class='header' role='banner' macro='gradient vert [[ColorPalette::PrimaryLight]] [[ColorPalette::PrimaryMid]]'>
<div class='headerShadow'>
<span class='siteTitle' refresh='content' tiddler='SiteTitle'></span>&nbsp;
<span class='siteSubtitle' refresh='content' tiddler='SiteSubtitle'></span>
</div>
<div class='headerForeground'>
<span class='siteTitle' refresh='content' tiddler='SiteTitle'></span>&nbsp;
<span class='siteSubtitle' refresh='content' tiddler='SiteSubtitle'></span>
</div>
</div>
<div id='mainMenu' role='navigation' refresh='content' tiddler='MainMenu'></div>
<div id='sidebar'>
<div id='sidebarOptions' role='navigation' refresh='content' tiddler='SideBarOptions'></div>
<div id='sidebarTabs' role='complementary' refresh='content' force='true' tiddler='SideBarTabs'></div>
</div>
<div id='displayArea' role='main'>
<div id='messageArea'></div>
<div id='tiddlerDisplay'></div>
</div>
<!--}}}-->
/*{{{*/
body {background:[[ColorPalette::Background]]; color:[[ColorPalette::Foreground]];}

a {color:[[ColorPalette::PrimaryMid]];}
a:hover {background-color:[[ColorPalette::PrimaryMid]]; color:[[ColorPalette::Background]];}
a img {border:0;}

h1,h2,h3,h4,h5,h6 {color:[[ColorPalette::SecondaryDark]]; background:transparent;}
h1 {border-bottom:2px solid [[ColorPalette::TertiaryLight]];}
h2,h3 {border-bottom:1px solid [[ColorPalette::TertiaryLight]];}

.button {color:[[ColorPalette::PrimaryDark]]; border:1px solid [[ColorPalette::Background]];}
.button:hover {color:[[ColorPalette::PrimaryDark]]; background:[[ColorPalette::SecondaryLight]]; border-color:[[ColorPalette::SecondaryMid]];}
.button:active {color:[[ColorPalette::Background]]; background:[[ColorPalette::SecondaryMid]]; border:1px solid [[ColorPalette::SecondaryDark]];}

.header {background:[[ColorPalette::PrimaryMid]];}
.headerShadow {color:[[ColorPalette::Foreground]];}
.headerShadow a {font-weight:normal; color:[[ColorPalette::Foreground]];}
.headerForeground {color:[[ColorPalette::Background]];}
.headerForeground a {font-weight:normal; color:[[ColorPalette::PrimaryPale]];}

.tabSelected {color:[[ColorPalette::PrimaryDark]];
	background:[[ColorPalette::TertiaryPale]];
	border-left:1px solid [[ColorPalette::TertiaryLight]];
	border-top:1px solid [[ColorPalette::TertiaryLight]];
	border-right:1px solid [[ColorPalette::TertiaryLight]];
}
.tabUnselected {color:[[ColorPalette::Background]]; background:[[ColorPalette::TertiaryMid]];}
.tabContents {color:[[ColorPalette::PrimaryDark]]; background:[[ColorPalette::TertiaryPale]]; border:1px solid [[ColorPalette::TertiaryLight]];}
.tabContents .button {border:0;}

#sidebar {}
#sidebarOptions input {border:1px solid [[ColorPalette::PrimaryMid]];}
#sidebarOptions .sliderPanel {background:[[ColorPalette::PrimaryPale]];}
#sidebarOptions .sliderPanel a {border:none;color:[[ColorPalette::PrimaryMid]];}
#sidebarOptions .sliderPanel a:hover {color:[[ColorPalette::Background]]; background:[[ColorPalette::PrimaryMid]];}
#sidebarOptions .sliderPanel a:active {color:[[ColorPalette::PrimaryMid]]; background:[[ColorPalette::Background]];}

.wizard {background:[[ColorPalette::PrimaryPale]]; border:1px solid [[ColorPalette::PrimaryMid]];}
.wizard h1 {color:[[ColorPalette::PrimaryDark]]; border:none;}
.wizard h2 {color:[[ColorPalette::Foreground]]; border:none;}
.wizardStep {background:[[ColorPalette::Background]]; color:[[ColorPalette::Foreground]];
	border:1px solid [[ColorPalette::PrimaryMid]];}
.wizardStep.wizardStepDone {background:[[ColorPalette::TertiaryLight]];}
.wizardFooter {background:[[ColorPalette::PrimaryPale]];}
.wizardFooter .status {background:[[ColorPalette::PrimaryDark]]; color:[[ColorPalette::Background]];}
.wizard .button {color:[[ColorPalette::Foreground]]; background:[[ColorPalette::SecondaryLight]]; border: 1px solid;
	border-color:[[ColorPalette::SecondaryPale]] [[ColorPalette::SecondaryDark]] [[ColorPalette::SecondaryDark]] [[ColorPalette::SecondaryPale]];}
.wizard .button:hover {color:[[ColorPalette::Foreground]]; background:[[ColorPalette::Background]];}
.wizard .button:active {color:[[ColorPalette::Background]]; background:[[ColorPalette::Foreground]]; border: 1px solid;
	border-color:[[ColorPalette::PrimaryDark]] [[ColorPalette::PrimaryPale]] [[ColorPalette::PrimaryPale]] [[ColorPalette::PrimaryDark]];}

.wizard .notChanged {background:transparent;}
.wizard .changedLocally {background:#80ff80;}
.wizard .changedServer {background:#8080ff;}
.wizard .changedBoth {background:#ff8080;}
.wizard .notFound {background:#ffff80;}
.wizard .putToServer {background:#ff80ff;}
.wizard .gotFromServer {background:#80ffff;}

#messageArea {border:1px solid [[ColorPalette::SecondaryMid]]; background:[[ColorPalette::SecondaryLight]]; color:[[ColorPalette::Foreground]];}
#messageArea .button {color:[[ColorPalette::PrimaryMid]]; background:[[ColorPalette::SecondaryPale]]; border:none;}

.popupTiddler {background:[[ColorPalette::TertiaryPale]]; border:2px solid [[ColorPalette::TertiaryMid]];}

.popup {background:[[ColorPalette::TertiaryPale]]; color:[[ColorPalette::TertiaryDark]]; border-left:1px solid [[ColorPalette::TertiaryMid]]; border-top:1px solid [[ColorPalette::TertiaryMid]]; border-right:2px solid [[ColorPalette::TertiaryDark]]; border-bottom:2px solid [[ColorPalette::TertiaryDark]];}
.popup hr {color:[[ColorPalette::PrimaryDark]]; background:[[ColorPalette::PrimaryDark]]; border-bottom:1px;}
.popup li.disabled {color:[[ColorPalette::TertiaryMid]];}
.popup li a, .popup li a:visited {color:[[ColorPalette::Foreground]]; border: none;}
.popup li a:hover {background:[[ColorPalette::SecondaryLight]]; color:[[ColorPalette::Foreground]]; border: none;}
.popup li a:active {background:[[ColorPalette::SecondaryPale]]; color:[[ColorPalette::Foreground]]; border: none;}
.popupHighlight {background:[[ColorPalette::Background]]; color:[[ColorPalette::Foreground]];}
.listBreak div {border-bottom:1px solid [[ColorPalette::TertiaryDark]];}

.tiddler .defaultCommand {font-weight:bold;}

.shadow .title {color:[[ColorPalette::TertiaryDark]];}

.title {color:[[ColorPalette::SecondaryDark]];}
.subtitle {color:[[ColorPalette::TertiaryDark]];}

.toolbar {color:[[ColorPalette::PrimaryMid]];}
.toolbar a {color:[[ColorPalette::TertiaryLight]];}
.selected .toolbar a {color:[[ColorPalette::TertiaryMid]];}
.selected .toolbar a:hover {color:[[ColorPalette::Foreground]];}

.tagging, .tagged {border:1px solid [[ColorPalette::TertiaryPale]]; background-color:[[ColorPalette::TertiaryPale]];}
.selected .tagging, .selected .tagged {background-color:[[ColorPalette::TertiaryLight]]; border:1px solid [[ColorPalette::TertiaryMid]];}
.tagging .listTitle, .tagged .listTitle {color:[[ColorPalette::PrimaryDark]];}
.tagging .button, .tagged .button {border:none;}

.footer {color:[[ColorPalette::TertiaryLight]];}
.selected .footer {color:[[ColorPalette::TertiaryMid]];}

.error, .errorButton {color:[[ColorPalette::Foreground]]; background:[[ColorPalette::Error]];}
.warning {color:[[ColorPalette::Foreground]]; background:[[ColorPalette::SecondaryPale]];}
.lowlight {background:[[ColorPalette::TertiaryLight]];}

.zoomer {background:none; color:[[ColorPalette::TertiaryMid]]; border:3px solid [[ColorPalette::TertiaryMid]];}

.imageLink, #displayArea .imageLink {background:transparent;}

.annotation {background:[[ColorPalette::SecondaryLight]]; color:[[ColorPalette::Foreground]]; border:2px solid [[ColorPalette::SecondaryMid]];}

.viewer .listTitle {list-style-type:none; margin-left:-2em;}
.viewer .button {border:1px solid [[ColorPalette::SecondaryMid]];}
.viewer blockquote {border-left:3px solid [[ColorPalette::TertiaryDark]];}

.viewer table, table.twtable {border:2px solid [[ColorPalette::TertiaryDark]];}
.viewer th, .viewer thead td, .twtable th, .twtable thead td {background:[[ColorPalette::SecondaryMid]]; border:1px solid [[ColorPalette::TertiaryDark]]; color:[[ColorPalette::Background]];}
.viewer td, .viewer tr, .twtable td, .twtable tr {border:1px solid [[ColorPalette::TertiaryDark]];}

.viewer pre {border:1px solid [[ColorPalette::SecondaryLight]]; background:[[ColorPalette::SecondaryPale]];}
.viewer code {color:[[ColorPalette::SecondaryDark]];}
.viewer hr {border:0; border-top:dashed 1px [[ColorPalette::TertiaryDark]]; color:[[ColorPalette::TertiaryDark]];}

.highlight, .marked {background:[[ColorPalette::SecondaryLight]];}

.editor input {border:1px solid [[ColorPalette::PrimaryMid]];}
.editor textarea {border:1px solid [[ColorPalette::PrimaryMid]]; width:100%;}
.editorFooter {color:[[ColorPalette::TertiaryMid]];}
.readOnly {background:[[ColorPalette::TertiaryPale]];}

#backstageArea {background:[[ColorPalette::Foreground]]; color:[[ColorPalette::TertiaryMid]];}
#backstageArea a {background:[[ColorPalette::Foreground]]; color:[[ColorPalette::Background]]; border:none;}
#backstageArea a:hover {background:[[ColorPalette::SecondaryLight]]; color:[[ColorPalette::Foreground]]; }
#backstageArea a.backstageSelTab {background:[[ColorPalette::Background]]; color:[[ColorPalette::Foreground]];}
#backstageButton a {background:none; color:[[ColorPalette::Background]]; border:none;}
#backstageButton a:hover {background:[[ColorPalette::Foreground]]; color:[[ColorPalette::Background]]; border:none;}
#backstagePanel {background:[[ColorPalette::Background]]; border-color: [[ColorPalette::Background]] [[ColorPalette::TertiaryDark]] [[ColorPalette::TertiaryDark]] [[ColorPalette::TertiaryDark]];}
.backstagePanelFooter .button {border:none; color:[[ColorPalette::Background]];}
.backstagePanelFooter .button:hover {color:[[ColorPalette::Foreground]];}
#backstageCloak {background:[[ColorPalette::Foreground]]; opacity:0.6; filter:alpha(opacity=60);}
/*}}}*/
/*{{{*/
* html .tiddler {height:1%;}

body {font-size:.75em; font-family:arial,helvetica; margin:0; padding:0;}

h1,h2,h3,h4,h5,h6 {font-weight:bold; text-decoration:none;}
h1,h2,h3 {padding-bottom:1px; margin-top:1.2em;margin-bottom:0.3em;}
h4,h5,h6 {margin-top:1em;}
h1 {font-size:1.35em;}
h2 {font-size:1.25em;}
h3 {font-size:1.1em;}
h4 {font-size:1em;}
h5 {font-size:.9em;}

hr {height:1px;}

a {text-decoration:none;}

dt {font-weight:bold;}

ol {list-style-type:decimal;}
ol ol {list-style-type:lower-alpha;}
ol ol ol {list-style-type:lower-roman;}
ol ol ol ol {list-style-type:decimal;}
ol ol ol ol ol {list-style-type:lower-alpha;}
ol ol ol ol ol ol {list-style-type:lower-roman;}
ol ol ol ol ol ol ol {list-style-type:decimal;}

.txtOptionInput {width:11em;}

#contentWrapper .chkOptionInput {border:0;}

.externalLink {text-decoration:underline;}

.indent {margin-left:3em;}
.outdent {margin-left:3em; text-indent:-3em;}
code.escaped {white-space:nowrap;}

.tiddlyLinkExisting {font-weight:bold;}
.tiddlyLinkNonExisting {font-style:italic;}

/* the 'a' is required for IE, otherwise it renders the whole tiddler in bold */
a.tiddlyLinkNonExisting.shadow {font-weight:bold;}

#mainMenu .tiddlyLinkExisting,
	#mainMenu .tiddlyLinkNonExisting,
	#sidebarTabs .tiddlyLinkNonExisting {font-weight:normal; font-style:normal;}
#sidebarTabs .tiddlyLinkExisting {font-weight:bold; font-style:normal;}

.header {position:relative;}
.header a:hover {background:transparent;}
.headerShadow {position:relative; padding:4.5em 0 1em 1em; left:-1px; top:-1px;}
.headerForeground {position:absolute; padding:4.5em 0 1em 1em; left:0; top:0;}

.siteTitle {font-size:3em;}
.siteSubtitle {font-size:1.2em;}

#mainMenu {position:absolute; left:0; width:10em; text-align:right; line-height:1.6em; padding:1.5em 0.5em 0.5em 0.5em; font-size:1.1em;}

#sidebar {position:absolute; right:3px; width:16em; font-size:.9em;}
#sidebarOptions {padding-top:0.3em;}
#sidebarOptions a {margin:0 0.2em; padding:0.2em 0.3em; display:block;}
#sidebarOptions input {margin:0.4em 0.5em;}
#sidebarOptions .sliderPanel {margin-left:1em; padding:0.5em; font-size:.85em;}
#sidebarOptions .sliderPanel a {font-weight:bold; display:inline; padding:0;}
#sidebarOptions .sliderPanel input {margin:0 0 0.3em 0;}
#sidebarTabs .tabContents {width:15em; overflow:hidden;}

.wizard {padding:0.1em 1em 0 2em;}
.wizard h1 {font-size:2em; font-weight:bold; background:none; padding:0; margin:0.4em 0 0.2em;}
.wizard h2 {font-size:1.2em; font-weight:bold; background:none; padding:0; margin:0.4em 0 0.2em;}
.wizardStep {padding:1em 1em 1em 1em;}
.wizard .button {margin:0.5em 0 0; font-size:1.2em;}
.wizardFooter {padding:0.8em 0.4em 0.8em 0;}
.wizardFooter .status {padding:0 0.4em; margin-left:1em;}
.wizard .button {padding:0.1em 0.2em;}

#messageArea {position:fixed; top:2em; right:0; margin:0.5em; padding:0.5em; z-index:2000; _position:absolute;}
.messageToolbar {display:block; text-align:right; padding:0.2em;}
#messageArea a {text-decoration:underline;}

.tiddlerPopupButton {padding:0.2em;}
.popupTiddler {position: absolute; z-index:300; padding:1em; margin:0;}

.popup {position:absolute; z-index:300; font-size:.9em; padding:0; list-style:none; margin:0;}
.popup .popupMessage {padding:0.4em;}
.popup hr {display:block; height:1px; width:auto; padding:0; margin:0.2em 0;}
.popup li.disabled {padding:0.4em;}
.popup li a {display:block; padding:0.4em; font-weight:normal; cursor:pointer;}
.listBreak {font-size:1px; line-height:1px;}
.listBreak div {margin:2px 0;}

.tabset {padding:1em 0 0 0.5em;}
.tab {margin:0 0 0 0.25em; padding:2px;}
.tabContents {padding:0.5em;}
.tabContents ul, .tabContents ol {margin:0; padding:0;}
.txtMainTab .tabContents li {list-style:none;}
.tabContents li.listLink { margin-left:.75em;}

#contentWrapper {display:block;}
#splashScreen {display:none;}

#displayArea {margin:1em 17em 0 14em;}

.toolbar {text-align:right; font-size:.9em;}

.tiddler {padding:1em 1em 0;}

.missing .viewer,.missing .title {font-style:italic;}

.title {font-size:1.6em; font-weight:bold;}

.missing .subtitle {display:none;}
.subtitle {font-size:1.1em;}

.tiddler .button {padding:0.2em 0.4em;}

.tagging {margin:0.5em 0.5em 0.5em 0; float:left; display:none;}
.isTag .tagging {display:block;}
.tagged {margin:0.5em; float:right;}
.tagging, .tagged {font-size:0.9em; padding:0.25em;}
.tagging ul, .tagged ul {list-style:none; margin:0.25em; padding:0;}
.tagClear {clear:both;}

.footer {font-size:.9em;}
.footer li {display:inline;}

.annotation {padding:0.5em; margin:0.5em;}

* html .viewer pre {width:99%; padding:0 0 1em 0;}
.viewer {line-height:1.4em; padding-top:0.5em;}
.viewer .button {margin:0 0.25em; padding:0 0.25em;}
.viewer blockquote {line-height:1.5em; padding-left:0.8em;margin-left:2.5em;}
.viewer ul, .viewer ol {margin-left:0.5em; padding-left:1.5em;}

.viewer table, table.twtable {border-collapse:collapse; margin:0.8em 1.0em;}
.viewer th, .viewer td, .viewer tr,.viewer caption,.twtable th, .twtable td, .twtable tr,.twtable caption {padding:3px;}
table.listView {font-size:0.85em; margin:0.8em 1.0em;}
table.listView th, table.listView td, table.listView tr {padding:0 3px 0 3px;}

.viewer pre {padding:0.5em; margin-left:0.5em; font-size:1.2em; line-height:1.4em; overflow:auto;}
.viewer code {font-size:1.2em; line-height:1.4em;}

.editor {font-size:1.1em;}
.editor input, .editor textarea {display:block; width:100%; font:inherit;}
.editorFooter {padding:0.25em 0; font-size:.9em;}
.editorFooter .button {padding-top:0; padding-bottom:0;}

.fieldsetFix {border:0; padding:0; margin:1px 0px;}

.zoomer {font-size:1.1em; position:absolute; overflow:hidden;}
.zoomer div {padding:1em;}

* html #backstage {width:99%;}
* html #backstageArea {width:99%;}
#backstageArea {display:none; position:relative; overflow: hidden; z-index:150; padding:0.3em 0.5em;}
#backstageToolbar {position:relative;}
#backstageArea a {font-weight:bold; margin-left:0.5em; padding:0.3em 0.5em;}
#backstageButton {display:none; position:absolute; z-index:175; top:0; right:0;}
#backstageButton a {padding:0.1em 0.4em; margin:0.1em;}
#backstage {position:relative; width:100%; z-index:50;}
#backstagePanel {display:none; z-index:100; position:absolute; width:90%; margin-left:3em; padding:1em;}
.backstagePanelFooter {padding-top:0.2em; float:right;}
.backstagePanelFooter a {padding:0.2em 0.4em;}
#backstageCloak {display:none; z-index:20; position:absolute; width:100%; height:100px;}

.whenBackstage {display:none;}
.backstageVisible .whenBackstage {display:block;}
/*}}}*/
/***
StyleSheet for use when a translation requires any css style changes.
This StyleSheet can be used directly by languages such as Chinese, Japanese and Korean which need larger font sizes.
***/
/*{{{*/
body {font-size:0.8em;}
#sidebarOptions {font-size:1.05em;}
#sidebarOptions a {font-style:normal;}
#sidebarOptions .sliderPanel {font-size:0.95em;}
.subtitle {font-size:0.8em;}
.viewer table.listView {font-size:0.95em;}
/*}}}*/
/*{{{*/
@media print {
#mainMenu, #sidebar, #messageArea, .toolbar, #backstageButton, #backstageArea {display: none !important;}
#displayArea {margin: 1em 1em 0em;}
noscript {display:none;} /* Fixes a feature in Firefox 1.5.0.2 where print preview displays the noscript content */
}
/*}}}*/
<!--{{{-->
<div class='toolbar' role='navigation' macro='toolbar [[ToolbarCommands::ViewToolbar]]'></div>
<div class='title' macro='view title'></div>
<div class='subtitle'><span macro='view modifier link'></span>, <span macro='view modified date'></span> (<span macro='message views.wikified.createdPrompt'></span> <span macro='view created date'></span>)</div>
<div class='tagging' macro='tagging'></div>
<div class='tagged' macro='tags'></div>
<div class='viewer' macro='view text wikified'></div>
<div class='tagClear'></div>
<!--}}}-->
''Use with extra care!''
|!|!Type|!Size (bits)|!Example|!Minimum Value|!Maximum Value|
||byte|8|byte b = 65;|-128|127|
||char([[*|Configurable 16 or 8 bit char type]])|16|char c = 'A'; char c = 65;|0|65535|
||short|16|short s = 65;|-32768|32767|
||int|16|int i = 65;|-32768|32767|
||long|16|long l = 65L;|-32768|32767|
||[[float|half precision float]]|16|float f = 65f;|-65504.0|65504.0|
||[[double|half precision double]]|16|double d = 65.55;|-65504.0|65504.0|
||boolean|8|boolean b = true;|>|true or false|
''Remark'' 
Nevertheless the reserved space on [[stack|Stack Layout]] for ''double'' and ''long'' is 2 * 16 Bit.
Recommended mode for 16 Bit micros.
|!|!Type|!Size (bits)|!Example|!Minimum Value|!Maximum Value|
||byte|8|byte b = 65;|-128|127|
||char([[*|Configurable 16 or 8 bit char type]])|16|char c = 'A'; char c = 65;|0|65535|
||short|16|short s = 65;|-32768|32767|
||int|16|int i = 65;|-32768|32767|
||long|32|long l = 65L;|-2147483648|2147483647|
||[[float|half precision float]]|16|float f = 65f;|-65504.0|65504.0|
||[[double|double 32]]|32|double d = 65.55;|>|+/- 1.4023x10^-45 to 3.4028x10^+38|
||boolean|8|boolean b = true;|>|true or false|
|!|!Type|!Size (bits)|!Example|!Minimum Value|!Maximum Value|
||byte|8|byte b = 65;|-128|127|
||char([[*|Configurable 16 or 8 bit char type]])|16|char c = 'A'; char c = 65;|0|65535|
||short|16|short s = 65;|-32768|32767|
||int|32|int i = 65;|-2147483648|2147483647|
||long|32|long l = 65L;|-2147483648|2147483647|
||float|32|float f = 65f;|>|+/- 1.4023x10^-45 to 3.4028x10^+38|
||[[double|double 32]]|32|double d = 65.55;|>|+/- 1.4023x10^-45 to 3.4028x10^+38|
||boolean|8|boolean b = true;|>|true or false|
''Remark'' 
Nevertheless the reserved space on [[stack|Stack Layout]] for ''double'' and ''long'' is 2 * 32 Bit.
|!|!Type|!Size (bits)|!Example|!Minimum Value|!Maximum Value|
||byte|8|byte b = 65;|-128|127|
||char([[*|Configurable 16 or 8 bit char type]])|16|char c = 'A'; char c = 65;|0|65535|
||short|16|short s = 65;|-32768|32767|
||int|32|int i = 65;|-2147483648|2147483647|
||long|64|long l = 65L;|-9223372036854775808|9223372036854775807|
||float|32|float f = 65f;|>|+/- 1.4023x10^-45 to 3.4028x10^+38|
||double|64|double d = 65.55;|>|+/- 4.9406x10^-324 to 1.7977x10^+308|
||boolean|8|boolean b = true;|>|true or false|

''Remark 1:'' 
~HaikuVM maps all primitive data types to corresponding C data types. For example JAVA type ''double'' is mapped to C type ''double''. This sounds obvious but may cause problems. ([[More ...|double and float support]])

''Remark 2:'' 
~HaikuVM makes extra effort to map the JAVA type ''long'' to a C type which has 64Bit precision. (Using C types 'long long' or 'int64_t' depending on the compiler).
!Meaning of the Directories
~HaikuVM comes with a set of directories as a conglomeration of multiple single-purpose projects. First ~HaikuVM consists of a couple of Java and C++ projects. Here I'll shed some light on the directories in haikuVM and what they are for:

''haikuVM''
*''bin''<br>For Windows and Linux commands (e.g. like haikulink) to be used with ~HaikuVM. ([[More ...|Commands]])
*''bootstrap''<br>A collection of ~MicroKernels and usefull microcontroller platform specific Java classes/libs. Often used (import) from the Java examples (see below).
*''config''<br>Central place for the configuration file '~HaikuVM.properties'. ([[More ...|HaikuVM.properties]])
*''examples''<br>Serves as a pool of example java files to be used as simple starter for your projects.
*''gallerie''<br>Short examples shared with the ~HaikuVM community. (Just send it via e-mail or use other ways.)
*''haikuBench''<br>Benchmarks and ~JUnits (mostly) for internal use.
*''haikufier''<br>Implementation of all the ~HaikuVM commands. This is the machine room of ~HaikuVM during compile and link time.
*''haikuRT''<br>This is the special ~HaikuVM runtime. The leJOS runtime is prefered but some core classes (like Thread, String, etc.) have to be tweeked/substituted for ~HaikuVM and ~AVRs and small RAM footprint. So haikuRT will precede classes.jar (see lib) in every classpath used with your project.
*''haikuVM''<br>C file templates used to be copied into your (empty) project directory to be cross compiled for your micro.  This is the machine room, the Java VM, of ~HaikuVM during runtime on the target micro itself.
*''hardware''<br>Service only for Windows users. Consists of WINAVR, AVRDUDE, AVR libs and include files. (Linux users have to install this separately, see [[here|Linux]].)
*''lib''
**jars<br>All this ~JAR-files needed for the commands in bin.
***classes.jar -> Java runtime as borrowed from the leJOS project.
***haikutools.jar -> Central place of all the ~HaikuVM commands as used in bin. Build from sources in haikufier.
***bcel-5.2.jar -> The BCEL project used in haikulink to disassemble class files.
**~C-LIBs and *.h include files<br>For Tutorials about Duemilanove and Leonardo using JNI via ~C-LIBs.
*''myCProject''<br>A template directory for your project (and tutorials). Any other ''empty'' directory, elsewhere on your disk, will do as well. ([[More ...|Your Project on Disk and at Runtime]])
Here Arduino stands for Arduino Duemilanove because the Duemilanove is the reference system of ~HaikuVM. Other Arduino flavors work as well.

This is about how to program a Duemilanove in JAVA (not using the [[Arduino IDE]]) to let the LED blink. This could be done easy without an extra thread. But just for example and because I'm proud of ~HaikuVM having Threads, I show this blink solution using a thread.
<code java>
package arduino.tutorial;

import static haiku.avr.lib.arduino.WProgram.*;

public class BlinkWithThread extends Thread {
    static byte ledPin = 13;            // LED connected to digital pin 13

    public void run()                   // run over and over again
    {
        while (true) {
            digitalWrite(ledPin, HIGH); // sets the LED on
            delay(1000);                // waits for a second
            digitalWrite(ledPin, LOW);  // sets the LED off
            delay(1000);                // waits for a second
        }
    }

    public static void main(String[] args) {
        pinMode(ledPin, OUTPUT);        // sets the digital pin as output
        new BlinkWithThread().start();
    }
}
</code>

After you have installed all needed software (see GettingStarted) you can proceed with the following 2 steps to let the ~BlinkWithThread program run on your Duemilanove:
<code bash>
cd C:\haikuVM\myCProject
C:\haikuVM\bin\haiku -v --Config arduino -o BlinkWithThread.hex C:\haikuVM\examples\src\main\java\arduino\tutorial\BlinkWithThread.java
</code>

*[[haiku]] first calls [[haikuc]] which calls javac to compile ''~BlinkWithThread.java'' into ''~BlinkWithThread.class'' (bytecode).
*[[haiku]] second calls [[haikulink]] which first translates the ''~BlinkWithThread.class'' into a ''C program'' and adds the Haiku VM (which is written also in C). Second it cross compiles and links all C sources into the file ''~BlinkWithThread.hex'' by calling 'make all' of WINAVR.
*[[haiku]] third calls [[haikuupload]] which finally uploads ''~BlinkWithThread.hex'' to the Arduino by calling avrdude.
Most of this steps are configurable in the file [[HaikuVM.properties]] or can be modified by giving other [[Command Line Options]]. For instance [[HaikuVM.properties]] assumes that your ARDUINO is connected on port com17. Change the following line of [[HaikuVM.properties]] to adapt to your configuration:
{{{
arduino.Port = com17
}}}
Or call [[haiku]] with a port name like this:
<code bash>
C:\haikuVM\bin\haiku -v --Config arduino --Config:Port com5 -o BlinkWithThread.hex C:\haikuVM\examples\src\main\java\arduino\tutorial\BlinkWithThread.java
</code>

For those who are curious to see how any Arduino can be programmed with JAVA and the [[Arduino IDE]], follow this [[link|Processing]].



After you have installed all needed software (see GettingStarted) you can alternativly proceed with the following 4 steps to let the ~BlinkWithThread program run on your Arduino:
<code bash>
cd C:\haikuVM\myCProject
C:\haikuVM\bin\haikuc                                               C:\haikuVM\examples\src\main\java\arduino\tutorial\BlinkWithThread.java
C:\haikuVM\bin\haikulink -v --Config arduino -o BlinkWithThread.hex C:\haikuVM\examples\src\main\java\arduino\tutorial\BlinkWithThread 
C:\haikuVM\bin\haikuupload                      BlinkWithThread.hex
</code>

*[[haikuc]] calls javac to compile ''~BlinkWithThread.java'' into ''~BlinkWithThread.class'' (bytecode).
*[[haikulink]] first translates the ''~BlinkWithThread.class'' into a ''C program'' and adds the Haiku VM (which is written also in C). Second it cross compiles and links all C sources into the file ''~BlinkWithThread.hex'' by calling make of WINAVR.
*[[haikuupload]] finally uploads ''~BlinkWithThread.hex'' to the Arduino by calling avrdude.
Most of this steps are configurable in the file [[HaikuVM.properties]] or can be modified by giving other [[Command Line Options]]. For instance [[HaikuVM.properties]] assumes that your ARDUINO is connected on port com17. Change the following line of [[HaikuVM.properties]] to adapt to your configuration:
{{{
arduino.Port = com17
}}}


I assume that you already have 
#installed your Arduino IDE 1.0.5 into '''C:\arduino-1.0.5''' or Arduino IDE 1.5.8 into '''C:\arduino-1.5.8'''. (But don't panic. It's not limited to these named directories. In fact one is free to choose any directory to install Arduino IDE in. In what follows, it's just a convenient named reference for me.)
#tested your Arduino IDE installation by successfully compile and upload at least one native processing sketch example shipped with the Arduino IDE (e.g. Blink) to your Arduino (e.g. Leonardo).
#downloaded and unziped ~HaikuVM into '''C:\haikuVM'''.
#made sure that a Java JDK is in your ~PATH-variable. 

<<<
''WARNING:'' if you use ''Win 8'' and installed the Arduino IDE in ''C:\Program Files (x86)\Arduino\libraries'', make sure if you have write permission in this directory:
<code bash>
cd C:\Program Files (x86)\Arduino\libraries
echo hello >test.txt
</code>
<<<

Using ~HaikuVM with the Arduino IDE is done in two phases:
#First, use ~HaikuVM to compile your Java program ("abuseing" ~HaikuVM as a ''~Java-to-C'' compiler) into the Arduino ''library'' directory (see below). The library directory ~HaikuVM then will include the freshly made processing sketch corresponding to your Java program.
#Second, (re-)start the Arduino IDE and compile and upload the freshly generated processing sketch found in directory ~HaikuVM. Make sure you select your Arduino hardware (e.g. Leonardo).

For a first test, please pick a prepared Java program, called 'Blink', from the ~HaikuVM examples using the 'arduinoIDE' configuration like this:
<code bash>
cd C:\arduino-1.0.5\libraries
C:\haikuVM\bin\haiku -v --Config arduinoIDE C:\haikuVM\examples\src\main\java\processing\examples\_01_Basics\Blink.java
</code>

This will install a new Arduino library called '~HaikuVM' with an example called '~HaikuVM' as well. Now start your Arduino IDE, navigate to library '~HaikuVM' and start and upload example '~HaikuVM' to your Arduino hardware. You should see the Arduino LED blink.

[img[images/ArduinoIDE.png]]

From here you may proceed with other examples from 'C:\haikuVM\examples\src\main\java\processing\examples' like this:
<code bash>
C:\haikuVM\bin\haiku -v --Config arduinoIDE C:\haikuVM\examples\src\main\java\processing\examples\_08_Strings\StringLengthTrim.java
</code>
This will overwrite the contents of the former generated Arduino library '~HaikuVM' (and its example '~HaikuVM') to reflect the new ~StringLengthTrim content.

After this, feel free to write your own Java programs, using the rich C++ libraries coming with the Arduino IDE. For those who want to learn more about seamless access of the rich C++ libraries coming with the Arduino IDE, I recommend reading the [[Tutorial JNI]].
This is how to program an Asuro (with an Atmega8) robot in JAVA (using the JAVA ported ~AsuroLib 2.8.0 rc1 [[which is originaly written in C|https://sourceforge.net/projects/asuro/]]).
<code java>
package asuro.tutorial;

import static haiku.avr.lib.asuro.lib2_8_0_rc1.AsuroLib2_8_0_rc1.*;

public class Blink {
    public static void main(String[] args) {
        Init(); // initialize the ASURO

        while (true) {
            StatusLED(GREEN);
            Msleep(1000);
            StatusLED(RED);
            Msleep(1000);
        }
    }
}
</code>

After you have installed all needed software (see GettingStarted) you can proceed with the following 5 steps to let the Blink program run on your ASURO:
<code bash>
cd C:\haikuVM\myCProject
C:\haikuVM\bin\haiku -v --Config asuro -o Blink.hex C:\haikuVM\examples\src\main\java\arduino\tutorial\Blink.java 
</code>
([[See an alternativ approach.|Asuro Details]])

*[[haiku]] first calls [[haikuc]] which calls javac to compile ''Blink.java'' into ''Blink.class'' (bytecode).
*[[haiku]] second calls [[haikulink]] which first translates the ''Blink.class'' into a ''C program'' and adds the Haiku VM (which is written also in C). Second it cross compiles and links all C sources into the file ''Blink.hex'' by calling make of WINAVR.
*[[haiku]] third calls [[haikuupload]] which finally uploads ''Blink.hex'' to the ASURO by calling ~ASUROFlash155.
Most of this steps are configurable in the file [[HaikuVM.properties|HaikuVM.properties]] or can be modified by giving other [[command line options|Command Line Options]].  For instance [[HaikuVM.properties]] assumes that your ASURO code is uploaded with ~ASUROFlash155.exe (not shipped with ~HaikuVM). Change the following line of [[HaikuVM.properties]] to adapt to your configuration:
{{{
asuro.Upload = cmd /c start ASUROFlash155
}}}

If you curious to see how the blinking can be achieved by ''using threads'', take a look into './examples/src/main/java/asuro/tutorial/~BlinkWithThread.java' and/or proceed like this:
<code bash>
C:\haikuVM\bin\haiku -v --Config asuro -o BlinkWithThread.hex C:\haikuVM\examples\src\main\java\arduino\tutorial\BlinkWithThread.java
</code>
After you have installed all needed software (see GettingStarted) you can alternativly proceed with the following 4 steps to let the Blink program run on your ASURO:
<code bash>
cd C:\haikuVM\myCProject
C:\haikuVM\bin\haikuc                                   C:\haikuVM\examples\src\main\java\arduino\tutorial\Blink.java
C:\haikuVM\bin\haikulink -v --Config asuro -o Blink.hex C:\haikuVM\examples\src\main\java\arduino\tutorial\Blink 
C:\haikuVM\bin\haikuupload                    Blink.hex
</code>

*[[haikuc]] calls javac to compile ''Blink.java'' into ''Blink.class'' (bytecode).
*[[haikulink]] first translates the ''Blink.class'' into a ''C program'' and adds the Haiku VM (which is written also in C). Second it cross compiles and links all C sources into the file ''Blink.hex'' by calling make of WINAVR.
*[[haikuupload]] finally uploads ''Blink.hex'' to the ASURO by calling ~ASUROFlash155.
Most of this steps are configurable in the file [[HaikuVM.properties|HaikuVM.properties]] or can be modified by giving other [[command line options|Command Line Options]].  For instance [[HaikuVM.properties]] assumes that your ASURO code is uploaded with ~ASUROFlash155.exe (not shipped with ~HaikuVM). Change the following line of [[HaikuVM.properties]] to adapt to your configuration:
{{{
asuro.Upload = cmd /c start ASUROFlash155
}}}

If you curious to see how the blinking can be achieved by ''using threads'', take a look into './examples/src/main/java/asuro/tutorial/~BlinkWithThread.java' and/or proceed like this:
<code bash>
C:\haikuVM\bin\haikuc                                             C:\haikuVM\examples\src\main\java\arduino\tutorial\BlinkWithThread.java
C:\haikuVM\bin\haikulink -v --Config asuro -o BlinkWithThread.hex C:\haikuVM\examples\src\main\java\arduino\tutorial\BlinkWithThread
C:\haikuVM\bin\haikuupload                    BlinkWithThread.hex
</code>
After you have installed all needed software (see GettingStarted) you are prepared to run the ''~BlinkSimple'' program on your AVR (e.g. ~ATmega328p).
<code java>
package avr.tutorial;
import static haiku.avr.AVRConstants.*;
public class BlinkSimple {
    private static final int LED = 1 << 5;

    private static void delay(int nounit) {
        while(nounit>0) {
            nounit--;
        }
    }

    public static void main(String[] args) {
        // Data direction of I/O-Port.
        DDRB = LED;
        while (true) {
            PORTB |= LED; // on
            delay(3000);
            PORTB &= ~LED; // off
            delay(30000);
        }
    }
}
</code>
''Caution:'' You may have to edit and change it to your needs because this example assumes that the LED is on PORTB.

You have to proceed with the following 4 steps to prepare and let the ''~BlinkSimple'' program run on your AVR.
<code bash>
cd C:\haikuVM\myCProject
C:\haikuVM\bin\haikuc                                             C:\haikuVM\examples\src\main\java\avr\tutorial\BlinkSimple.java
C:\haikuVM\bin\haikulink -v --Config simple010 -o BlinkSimple.hex C:\haikuVM\examples\src\main\java\avr\tutorial\BlinkSimple 
C:\haikuVM\bin\haikuupload                        BlinkSimple.hex
</code>
This is what happens:
*[[haikuc]] calls javac to compile ''~BlinkSimple.java'' into ''~BlinkSimple.class'' (bytecode).
*[[haikulink]] first translates the ''~BlinkSimple.class'' into a ''C program'' and adds the Haiku VM (which is written also in C). Second it cross compiles and links all C sources into the file ''~BlinkSimple.hex'' by calling make of WINAVR.
*[[haikuupload]] finally uploads ''~BlinkSimple.hex'' to the AVR by calling avrdude.
Most of this steps are configurable in the file [[HaikuVM.properties|HaikuVM.properties]] or can be modified by giving other [[command line options|Command Line Options]].  For instance [[HaikuVM.properties]] assumes that your AVR code is uploaded with avrdude. Change the following line of [[HaikuVM.properties]] to adapt to your configuration:
{{{
simple010.Upload = ...
}}}

This code of ''~BlinkSimple.java'' uses a simple busy-wait delay loop to let the LED blink.

From here you might proceed with 'C:\haikuVM\examples\src\main\java\avr\tutorial\Blink.java'. Which uses Thread.sleep(..) for handling delays, which in turn relies on timer 0 overflow interrupt (resulting in non-busy-wait).
Background: #fff
Foreground: #000
PrimaryPale: #8cf
PrimaryLight: #18f
PrimaryMid: #04b
PrimaryDark: #014
SecondaryPale: #ffc
SecondaryLight: #fe8
SecondaryMid: #db4
SecondaryDark: #841
TertiaryPale: #eee
TertiaryLight: #ccc
TertiaryMid: #999
TertiaryDark: #666
Error: #f88
This are typical configuration options you may want to set with the commandline option {{{--Config:<propertyname> <value>}}} where <propertyname> is one of:
*Char
*Clock
*Config
*Extension
*GC
*~InitialMainThreadStackSize
*~InitialOtherThreadStackSize
*~MemorySize
*~MicroKernel
*Mode
*~PanicExceptions
*~PanicSupport
*Port
*Target
*Threads
*~TimerInterrupt
Example:
{{{--Config:Char 2}}}
!Char
For configurable 16 or 8 bit char type. Possible values are [[More ...|Configurable 16 or 8 bit char type]]
*~HAIKU_CHAR_16 | ~HAIKU_CHAR_2 | 16 | 2<br>Characters need 2 Bytes (for JAVA compliants)
*''~HAIKU_CHAR_8 | ~HAIKU_CHAR_1 | 8 | 1''<br>Characters need 1 Byte (Default and most convenient for micros)
!Clock
Clock frequence of the microcontoller in Hz (e.g. use 16000000 for 16 ~MHz) to be used for the cross compiler.
!Config
{{{--Config:Config arduino}}}
same as
{{{--Config arduino}}}
!Extension
Defines the file extension of the result of [[haikulink]] step. (Default is 'hex'.)
!GC
To set the type of garbage collection [[More ...|Garbage collection]]
*~HAIKU_NoGC<br>No GC (no garbage collection at all)
*''~HAIKU_ConservativGC''<br>Stop the world GC (default)
*~HAIKU_IncrementalGC<br>Incremental GC (slices of work of the GC are done between interpretation of bytecodes)
*~HAIKU_CompactingGC<br>Stop the world compacting GC (experimental)
!~InitialMainThreadStackSize
In general ~HaikuVM allocates a [[stack frame|Stack Layout]] for each function called. This works perfect because JAVA knows the maximum stack size needed for each function in advance. One drawback is heap fragmentation. Another is wasted time to allocate all this tiny stack frame on heap. But, befor doing so ~HaikuVM uses the initial stack given for the main thread. The size of this stack is defined by property ~InitialMainThreadStackSize. To optimize speed and heap fragmentation you may size this initial stack segment to your needs. Default is a size of 145 ints (new int[~InitialMainThreadStackSize]).
!~InitialOtherThreadStackSize
Same as ~InitialMainThreadStackSize but for all other threads.
!~MemorySize
Is the overall stack and heap size in bytes of RAM which ~HaikuVM may use. For ~AVRs default is '(RAMEND - 0x100) - 300'. So, 300 bytes are reserved for the internal use of the Haiku VM itself. [[More ...|Your Project on Disk and at Runtime]]
!~MicroKernel
To define your wanted [[MicroKernel|Tutorial All About MicroKernels]] class on commandline e.g.:
{{{--Config:MicroKernel haiku.avr.lib.simple010.HaikuMicroKernel}}} 
!Mode
For configurable 64, 32 or 16 bit data types [[More ...|Configurable 64, 32 or 16 bit data types]]
*~HAIKU_32_64 | 32/64<br>for JAVA compliants
*~HAIKU_32_32 | 32/32
*''~HAIKU_16_32 | 16/32''<br>default and most convenient for micros
*~HAIKU_16_16 | 16/16
!~PanicExceptions
The Haiku VM itself is written in C but, some data conditions are detected to be signaled as JAVA exceptions into your JAVA code. Here is a complete list of supported internal exceptions:
*~NullPointerException
*~ArrayStoreException
*~IndexOutOfBoundsException
*~NoSuchMethodError
*~StackOverflowError
*~OutOfMemoryError
*~ClassCastException
*~ArrayIndexOutOfBoundsException
*~VirtualMachineError
*~ArithmeticException
If you want that some of this exceptions should be thrown into your JAVA they should be or-ed into ~PanicExceptions e.g. like this:
{{{--Config:PanicExceptions "NullPointerException|NoSuchMethodError|OutOfMemoryError|ClassCastException|VirtualMachineError|ArrayIndexOutOfBoundsException|StackOverflowError"}}}
!~PanicSupport
Convenient flag to switch the list given with ~PanicExceptions on and off.
*''0'' no exceptions, given with ~PanicExceptions, are thrown internally.
*1 internal exceptions, given with ~PanicExceptions, are thrown.
!Port
Is the device Name for flashing your microcontroller. For example write {{{--Config:Port com5}}} to use port '~COM5:' in WINDOWS.
Write {{{--Config:Port /dev/ttyUSB0}}} to use port '/dev/ttyUSB0' in UNIX. 
Sometimes it doesn't make sense to specify a port at all, because your microcontroller has to be flashed with a special tool. E.g. the ASURO Robot has to be flashed with ~ASUROFlash155.
!Target
Is the target code of your microcontroller to be used for the cross compiler.
!Threads
~HaikuVM automatically detects if thread support is needed for your program. 
*0
*1
If you want to force thread support use:
{{{--Config:Threads 1}}}
!~TimerInterrupt
On a microcontroller timer interrupts ([[More ...|Tutorial Interrupts]]) are used to support timing functions. [[More ...|Tutorial Timing]]
*''undef''<br>Default: no timer interrups are used.
*~TIMER0_OVF_vect<br>Default for most AVR configurations ([[More ...|HaikuVM.properties]]).
You may overwrite this on commandline like this:
{{{--Config:TimerInterrupt TIMER2_OVF_vect}}}
When it comes to the commands, ~HaikuVM doesn't re-event the wheel. Instead commands and their meaning is analog to leJOS. 

This are the leJOS NXJ tools for compiling, linking and uploading of programs:
* nxjc
* nxjlink
* nxjupload
* nxj
Corresponding to this the ~HaikuVM tools are:
* [[haikuc]]
* [[haikulink]]
* [[haikuupload]]
* [[haiku]]
For a more detailed description you can follow the desciption of the leJOS commands which can be found [[here|http://lejos.sourceforge.net/nxt/nxj/tutorial/Preliminaries/CompileAndRun.htm]].

If you take a look at the following JAVA code:
<code java>
package haikuvm.bench;

public class Fibonacci32Bit {
  static int fib(int n) {
    if(n < 2) 
      return 1;
    else
      return fib(n-2) + fib(n-1);
  } 

  public static void main(String[] args) {
	long t0 = System.currentTimeMillis();
    for(int i=0;i<=30;i++)
      System.out.println("Fibonacci of "+i+" is "+fib(i)+" in "+(System.currentTimeMillis()-t0)+" ms");
  }
}
</code>
Then javap says:
<code bash>
javap -c -classpath C:\haikuVM\haikuBench\bin haikuvm\bench\Fibonacci32Bit
</code>
That the bytecode in ~Fibonacci32Bit.class sums up to 97 bytes:
<code bash>
Compiled from "Fibonacci32Bit.java"
public class haikuvm.bench.Fibonacci32Bit extends java.lang.Object{
public haikuvm.bench.Fibonacci32Bit();
  Code:
   0:   aload_0
   1:   invokespecial   #8; //Method java/lang/Object."<init>":()V
   4:   return

static int fib(int);
  Code:
   0:   iload_0
   1:   iconst_2
   2:   if_icmpge       7
   5:   iconst_1
   6:   ireturn
   7:   iload_0
   8:   iconst_2
   9:   isub
   10:  invokestatic    #16; //Method fib:(I)I
   13:  iload_0
   14:  iconst_1
   15:  isub
   16:  invokestatic    #16; //Method fib:(I)I
   19:  iadd
   20:  ireturn

public static void main(java.lang.String[]);
  Code:
   0:   invokestatic    #23; //Method java/lang/System.currentTimeMillis:()J
   3:   lstore_1
   4:   iconst_0
   5:   istore_3
   6:   goto    64
   9:   getstatic       #29; //Field java/lang/System.out:Ljava/io/PrintStream;
   12:  new     #33; //class java/lang/StringBuilder
   15:  dup
   16:  ldc     #35; //String Fibonacci of
   18:  invokespecial   #37; //Method java/lang/StringBuilder."<init>":(Ljava/lang/String;)V
   21:  iload_3
   22:  invokevirtual   #40; //Method java/lang/StringBuilder.append:(I)Ljava/lang/StringBuilder;
   25:  ldc     #44; //String  is
   27:  invokevirtual   #46; //Method java/lang/StringBuilder.append:(Ljava/lang/String;)Ljava/lang/StringBuilder;
   30:  iload_3
   31:  invokestatic    #16; //Method fib:(I)I
   34:  invokevirtual   #40; //Method java/lang/StringBuilder.append:(I)Ljava/lang/StringBuilder;
   37:  ldc     #49; //String  in
   39:  invokevirtual   #46; //Method java/lang/StringBuilder.append:(Ljava/lang/String;)Ljava/lang/StringBuilder;
   42:  invokestatic    #23; //Method java/lang/System.currentTimeMillis:()J
   45:  lload_1
   46:  lsub
   47:  invokevirtual   #51; //Method java/lang/StringBuilder.append:(J)Ljava/lang/StringBuilder;
   50:  ldc     #54; //String  ms
   52:  invokevirtual   #46; //Method java/lang/StringBuilder.append:(Ljava/lang/String;)Ljava/lang/StringBuilder;
   55:  invokevirtual   #56; //Method java/lang/StringBuilder.toString:()Ljava/lang/String;
   58:  invokevirtual   #60; //Method java/io/PrintStream.println:(Ljava/lang/String;)V
   61:  iinc    3, 1
   64:  iload_3
   65:  bipush  30
   67:  if_icmple       9
   70:  return
}
</code>

^^For those who are curious to know how this is coded in ~HaikuVM should take a look [[here|Compact HaikuVM Code]].^^

If you compare this with a corresponding C program:
<code c>
int32_t fib(int32_t n) {
	if(n < 2) 
	  return 1;
	else
	  return fib(n-2) + fib(n-1);
} 

int fib_main() {
	int32_t i;
	long t0 = millis();
	for(i=0;i<=30;i++) {
          printf("Fibonacci of %ld is %ld in %ld ms\n", i, fib(i), (long)(millis()-t0));
	}
	return 0;
}
</code>
Then a disassembly listing says:
<code bash>
000001e0 <fib>:
 1e0:	af 92       	push	r10
 1e2:	bf 92       	push	r11
 1e4:	cf 92       	push	r12
 1e6:	df 92       	push	r13
 1e8:	ef 92       	push	r14
 1ea:	ff 92       	push	r15
 1ec:	0f 93       	push	r16
 1ee:	1f 93       	push	r17
 1f0:	7b 01       	movw	r14, r22
 1f2:	8c 01       	movw	r16, r24
 1f4:	aa 24       	eor	r10, r10
 1f6:	bb 24       	eor	r11, r11
 1f8:	65 01       	movw	r12, r10
 1fa:	82 e0       	ldi	r24, 0x02	; 2
 1fc:	e8 16       	cp	r14, r24
 1fe:	f1 04       	cpc	r15, r1
 200:	01 05       	cpc	r16, r1
 202:	11 05       	cpc	r17, r1
 204:	b4 f0       	brlt	.+44     	; 0x232 <fib+0x52>
 206:	8e ef       	ldi	r24, 0xFE	; 254
 208:	9f ef       	ldi	r25, 0xFF	; 255
 20a:	af ef       	ldi	r26, 0xFF	; 255
 20c:	bf ef       	ldi	r27, 0xFF	; 255
 20e:	e8 0e       	add	r14, r24
 210:	f9 1e       	adc	r15, r25
 212:	0a 1f       	adc	r16, r26
 214:	1b 1f       	adc	r17, r27
 216:	c8 01       	movw	r24, r16
 218:	b7 01       	movw	r22, r14
 21a:	0e 94 f0 00 	call	0x1e0	; 0x1e0 <fib>
 21e:	08 94       	sec
 220:	e1 1c       	adc	r14, r1
 222:	f1 1c       	adc	r15, r1
 224:	01 1d       	adc	r16, r1
 226:	11 1d       	adc	r17, r1
 228:	a6 0e       	add	r10, r22
 22a:	b7 1e       	adc	r11, r23
 22c:	c8 1e       	adc	r12, r24
 22e:	d9 1e       	adc	r13, r25
 230:	e4 cf       	rjmp	.-56     	; 0x1fa <fib+0x1a>
 232:	a6 01       	movw	r20, r12
 234:	95 01       	movw	r18, r10
 236:	2f 5f       	subi	r18, 0xFF	; 255
 238:	3f 4f       	sbci	r19, 0xFF	; 255
 23a:	4f 4f       	sbci	r20, 0xFF	; 255
 23c:	5f 4f       	sbci	r21, 0xFF	; 255
 23e:	b9 01       	movw	r22, r18
 240:	ca 01       	movw	r24, r20
 242:	1f 91       	pop	r17
 244:	0f 91       	pop	r16
 246:	ff 90       	pop	r15
 248:	ef 90       	pop	r14
 24a:	df 90       	pop	r13
 24c:	cf 90       	pop	r12
 24e:	bf 90       	pop	r11
 250:	af 90       	pop	r10
 252:	08 95       	ret

...

000002d0 <fib_main>:
 2d0:	2f 92       	push	r2
 2d2:	3f 92       	push	r3
 2d4:	4f 92       	push	r4
 2d6:	5f 92       	push	r5
 2d8:	6f 92       	push	r6
 2da:	7f 92       	push	r7
 2dc:	8f 92       	push	r8
 2de:	9f 92       	push	r9
 2e0:	af 92       	push	r10
 2e2:	bf 92       	push	r11
 2e4:	cf 92       	push	r12
 2e6:	df 92       	push	r13
 2e8:	ef 92       	push	r14
 2ea:	ff 92       	push	r15
 2ec:	0f 93       	push	r16
 2ee:	1f 93       	push	r17
 2f0:	cf 93       	push	r28
 2f2:	df 93       	push	r29
 2f4:	0e 94 b0 00 	call	0x160	; 0x160 <millis>
 2f8:	1b 01       	movw	r2, r22
 2fa:	2c 01       	movw	r4, r24
 2fc:	ee 24       	eor	r14, r14
 2fe:	ff 24       	eor	r15, r15
 300:	87 01       	movw	r16, r14
 302:	66 24       	eor	r6, r6
 304:	77 24       	eor	r7, r7
 306:	43 01       	movw	r8, r6
 308:	c0 e0       	ldi	r28, 0x00	; 0
 30a:	d1 e0       	ldi	r29, 0x01	; 1
 30c:	5c c0       	rjmp	.+184    	; 0x3c6 <fib_main+0xf6>
 30e:	22 e0       	ldi	r18, 0x02	; 2
 310:	e2 16       	cp	r14, r18
 312:	f1 04       	cpc	r15, r1
 314:	01 05       	cpc	r16, r1
 316:	11 05       	cpc	r17, r1
 318:	b4 f0       	brlt	.+44     	; 0x346 <fib_main+0x76>
 31a:	8e ef       	ldi	r24, 0xFE	; 254
 31c:	9f ef       	ldi	r25, 0xFF	; 255
 31e:	af ef       	ldi	r26, 0xFF	; 255
 320:	bf ef       	ldi	r27, 0xFF	; 255
 322:	e8 0e       	add	r14, r24
 324:	f9 1e       	adc	r15, r25
 326:	0a 1f       	adc	r16, r26
 328:	1b 1f       	adc	r17, r27
 32a:	c8 01       	movw	r24, r16
 32c:	b7 01       	movw	r22, r14
 32e:	0e 94 f0 00 	call	0x1e0	; 0x1e0 <fib>
 332:	08 94       	sec
 334:	e1 1c       	adc	r14, r1
 336:	f1 1c       	adc	r15, r1
 338:	01 1d       	adc	r16, r1
 33a:	11 1d       	adc	r17, r1
 33c:	a6 0e       	add	r10, r22
 33e:	b7 1e       	adc	r11, r23
 340:	c8 1e       	adc	r12, r24
 342:	d9 1e       	adc	r13, r25
 344:	e4 cf       	rjmp	.-56     	; 0x30e <fib_main+0x3e>
 346:	0e 94 b0 00 	call	0x160	; 0x160 <millis>
 34a:	ad b7       	in	r26, 0x3d	; 61
 34c:	be b7       	in	r27, 0x3e	; 62
 34e:	1e 97       	sbiw	r26, 0x0e	; 14
 350:	0f b6       	in	r0, 0x3f	; 63
 352:	f8 94       	cli
 354:	be bf       	out	0x3e, r27	; 62
 356:	0f be       	out	0x3f, r0	; 63
 358:	ad bf       	out	0x3d, r26	; 61
 35a:	ed b7       	in	r30, 0x3d	; 61
 35c:	fe b7       	in	r31, 0x3e	; 62
 35e:	31 96       	adiw	r30, 0x01	; 1
 360:	12 96       	adiw	r26, 0x02	; 2
 362:	dc 93       	st	X, r29
 364:	ce 93       	st	-X, r28
 366:	11 97       	sbiw	r26, 0x01	; 1
 368:	62 82       	std	Z+2, r6	; 0x02
 36a:	73 82       	std	Z+3, r7	; 0x03
 36c:	84 82       	std	Z+4, r8	; 0x04
 36e:	95 82       	std	Z+5, r9	; 0x05
 370:	08 94       	sec
 372:	a1 1c       	adc	r10, r1
 374:	b1 1c       	adc	r11, r1
 376:	c1 1c       	adc	r12, r1
 378:	d1 1c       	adc	r13, r1
 37a:	a6 82       	std	Z+6, r10	; 0x06
 37c:	b7 82       	std	Z+7, r11	; 0x07
 37e:	c0 86       	std	Z+8, r12	; 0x08
 380:	d1 86       	std	Z+9, r13	; 0x09
 382:	62 19       	sub	r22, r2
 384:	73 09       	sbc	r23, r3
 386:	84 09       	sbc	r24, r4
 388:	95 09       	sbc	r25, r5
 38a:	62 87       	std	Z+10, r22	; 0x0a
 38c:	73 87       	std	Z+11, r23	; 0x0b
 38e:	84 87       	std	Z+12, r24	; 0x0c
 390:	95 87       	std	Z+13, r25	; 0x0d
 392:	0e 94 2a 01 	call	0x254	; 0x254 <jprintf>
 396:	84 01       	movw	r16, r8
 398:	73 01       	movw	r14, r6
 39a:	08 94       	sec
 39c:	e1 1c       	adc	r14, r1
 39e:	f1 1c       	adc	r15, r1
 3a0:	01 1d       	adc	r16, r1
 3a2:	11 1d       	adc	r17, r1
 3a4:	2d b7       	in	r18, 0x3d	; 61
 3a6:	3e b7       	in	r19, 0x3e	; 62
 3a8:	22 5f       	subi	r18, 0xF2	; 242
 3aa:	3f 4f       	sbci	r19, 0xFF	; 255
 3ac:	0f b6       	in	r0, 0x3f	; 63
 3ae:	f8 94       	cli
 3b0:	3e bf       	out	0x3e, r19	; 62
 3b2:	0f be       	out	0x3f, r0	; 63
 3b4:	2d bf       	out	0x3d, r18	; 61
 3b6:	3f e1       	ldi	r19, 0x1F	; 31
 3b8:	e3 16       	cp	r14, r19
 3ba:	f1 04       	cpc	r15, r1
 3bc:	01 05       	cpc	r16, r1
 3be:	11 05       	cpc	r17, r1
 3c0:	31 f0       	breq	.+12     	; 0x3ce <fib_main+0xfe>
 3c2:	37 01       	movw	r6, r14
 3c4:	48 01       	movw	r8, r16
 3c6:	aa 24       	eor	r10, r10
 3c8:	bb 24       	eor	r11, r11
 3ca:	65 01       	movw	r12, r10
 3cc:	a0 cf       	rjmp	.-192    	; 0x30e <fib_main+0x3e>
 3ce:	df 91       	pop	r29
 3d0:	cf 91       	pop	r28
 3d2:	1f 91       	pop	r17
 3d4:	0f 91       	pop	r16
 3d6:	ff 90       	pop	r15
 3d8:	ef 90       	pop	r14
 3da:	df 90       	pop	r13
 3dc:	cf 90       	pop	r12
 3de:	bf 90       	pop	r11
 3e0:	af 90       	pop	r10
 3e2:	9f 90       	pop	r9
 3e4:	8f 90       	pop	r8
 3e6:	7f 90       	pop	r7
 3e8:	6f 90       	pop	r6
 3ea:	5f 90       	pop	r5
 3ec:	4f 90       	pop	r4
 3ee:	3f 90       	pop	r3
 3f0:	2f 90       	pop	r2
 3f2:	08 95       	ret
</code>
that the binary size for only this two functions (not including library code) sums up to 407 bytes for an AVR ~ATmega328p.

Conclusion: This ~HaikuVM program is ''about 4 times more compact'' than a plain C program (without counting library overhead). 
Given, for example, the following JAVA code:
<code java>
package haikuvm.bench;

public class Fibonacci32Bit {
  static int fib(int n) {
    if(n < 2) 
      return 1;
    else
      return fib(n-2) + fib(n-1);
  } 

  public static void main(String[] args) {
	long t0 = System.currentTimeMillis();
    for(int i=0;i<=30;i++)
      System.out.println("Fibonacci of "+i+" is "+fib(i)+" in "+(System.currentTimeMillis()-t0)+" ms");
  }
}
</code>

Then [[haikulink]] transformes the resulting bytecode into initialized plain C structs like this:
<code c>
/**
static int fib(int n)
Code(max_stack = 3, max_locals = 1, code_length = 21)
*/
const           haikuvm_bench_Fibonacci32Bit_fib_II_t haikuvm_bench_Fibonacci32Bit_fib_II PROGMEM ={
3+1 +2,    0,    1,    // max_stack, purLocals, purParams

OP_ILOAD_0,                                                            // 0:    iload_0
OP_ICONST_2,                                                           // 1:    iconst_2
OP_IF_ICMPGE,        TARGET(7),                                        // 2:    if_icmpge		#7
OP_ICONST_1,                                                           // 5:    iconst_1
OP_IRETURN,                                                            // 6:    ireturn
OP_ILOAD_0,                                                            // 7:    iload_0
OP_ICONST_2,                                                           // 8:    iconst_2
OP_ISUB,                                                               // 9:    isub
OP_INVOKESHORT_haikuvm_bench_Fibonacci32Bit_fib_II,                    // 10:   invokestatic	haikuvm.bench.Fibonacci32Bit.fib (I)I (16)
OP_ILOAD_0,                                                            // 13:   iload_0
OP_ICONST_1,                                                           // 14:   iconst_1
OP_ISUB,                                                               // 15:   isub
OP_INVOKESHORT_haikuvm_bench_Fibonacci32Bit_fib_II,                    // 16:   invokestatic	haikuvm.bench.Fibonacci32Bit.fib (I)I (16)
OP_IADD,                                                               // 19:   iadd
OP_IRETURN,                                                            // 20:   ireturn
};

/**
public static void main(String[] args)
Code(max_stack = 6, max_locals = 4, code_length = 71)
*/
const           haikuvm_bench_Fibonacci32Bit_main_YLjava_lang_String_V_t haikuvm_bench_Fibonacci32Bit_main_YLjava_lang_String_V PROGMEM ={
6+4 +2,    3,    1,    // max_stack, purLocals, purParams

OP_INVOKESHORT_java_lang_System_currentTimeMillis_J,                   // 0:    invokestatic	java.lang.System.currentTimeMillis ()J (23)
OP_LSTORE_1,                                                           // 3:    lstore_1
OP_ICONST_0,                                                           // 4:    iconst_0
OP_ISTORE_3,                                                           // 5:    istore_3
OP_GOTO,             TARGET(64),                                       // 6:    goto		#64
OP_GETSTATIC_L,      SADR(java_lang_System_out),                       // 9:    getstatic		java.lang.System.out Ljava/io/PrintStream; (29)
OP_NEW,              ADR(java_lang_StringBuilder__class),              // 12:   new		<java.lang.StringBuilder> (33)
OP_DUP,                                                                // 15:   dup
OP_LDC_S,            CADR(Const0005),                                  // 16:   ldc		"Fibonacci of " (35)
OP_INVOKESHORT_java_lang_StringBuilder__init__Ljava_lang_String_V,     // 18:   invokespecial	java.lang.StringBuilder.<init> (Ljava/lang/String;)V (37)
OP_ILOAD_3,                                                            // 21:   iload_3
OP_INVOKEVIRTUAL,    B(1), LB(MSG_append__I_Ljava_lang_StringBuilder), 
                                                                       // 22:   invokevirtual	java.lang.StringBuilder.append (I)Ljava/lang/StringBuilder; (40)
OP_LDC_S,            CADR(Const0006),                                  // 25:   ldc		" is " (44)
OP_INVOKEVIRTUAL,    B(1), LB(MSG_append__Ljava_lang_String__Ljava_lang_StringBuilder), 
                                                                       // 27:   invokevirtual	java.lang.StringBuilder.append (Ljava/lang/String;)Ljava/lang/StringBuilder; (46)
OP_ILOAD_3,                                                            // 30:   iload_3
OP_INVOKESHORT_haikuvm_bench_Fibonacci32Bit_fib_II,                    // 31:   invokestatic	haikuvm.bench.Fibonacci32Bit.fib (I)I (16)
OP_INVOKEVIRTUAL,    B(1), LB(MSG_append__I_Ljava_lang_StringBuilder), 
                                                                       // 34:   invokevirtual	java.lang.StringBuilder.append (I)Ljava/lang/StringBuilder; (40)
OP_LDC_S,            CADR(Const0007),                                  // 37:   ldc		" in " (49)
OP_INVOKEVIRTUAL,    B(1), LB(MSG_append__Ljava_lang_String__Ljava_lang_StringBuilder), 
                                                                       // 39:   invokevirtual	java.lang.StringBuilder.append (Ljava/lang/String;)Ljava/lang/StringBuilder; (46)
OP_INVOKESHORT_java_lang_System_currentTimeMillis_J,                   // 42:   invokestatic	java.lang.System.currentTimeMillis ()J (23)
OP_LLOAD_1,                                                            // 45:   lload_1
OP_LSUB,                                                               // 46:   lsub
OP_INVOKEVIRTUAL,    B(2), LB(MSG_append__J_Ljava_lang_StringBuilder), 
                                                                       // 47:   invokevirtual	java.lang.StringBuilder.append (J)Ljava/lang/StringBuilder; (51)
OP_LDC_S,            CADR(Const0008),                                  // 50:   ldc		" ms" (54)
OP_INVOKEVIRTUAL,    B(1), LB(MSG_append__Ljava_lang_String__Ljava_lang_StringBuilder), 
                                                                       // 52:   invokevirtual	java.lang.StringBuilder.append (Ljava/lang/String;)Ljava/lang/StringBuilder; (46)
OP_INVOKEVIRTUAL,    B(0), LB(MSG_toString___Ljava_lang_String),       // 55:   invokevirtual	java.lang.StringBuilder.toString ()Ljava/lang/String; (56)
OP_INVOKEVIRTUAL,    B(1), LB(MSG_println__Ljava_lang_String__V),      // 58:   invokevirtual	java.io.PrintStream.println (Ljava/lang/String;)V (60)
OP_IINC1, B(3),                                                        // 61:   iinc		%3	1
OP_ILOAD_3,                                                            // 64:   iload_3
OP_BIPUSH,           B(30),                                            // 65:   bipush		30
OP_IF_ICMPLE,        TARGET(9),                                        // 67:   if_icmple		#9
OP_RETURN,                                                             // 70:   return
};

const class_t haikuvm_bench_Fibonacci32Bit__class PROGMEM = {
	& java_lang_Object__class,
	sizeof(haikuvm_bench_Fibonacci32Bit),
	0,
};
</code>
~HaikuVM supports two char type sizes for char arrays (arrays only):
*~HAIKU_CHAR_16  (for JAVA compliants)
*~HAIKU_CHAR_8 (default and most convenient for ~AVRs)
The used char type size for arrays can be configured in the [[HaikuVM.properties]] file or as [[command line option|Command Line Options]].
This will ''not'' affect the size of a basic char type when not stored in an array. This flag was invented only to reduce the size of char arrays.
~HaikuVM supports four memory modes:
#[[32/64 (for JAVA compliants)]]
#[[32/32]]
#[[16/32 (default and most convenient for micros)]]
#[[16/16]]

|!Overview|>|>|>|>|>|>|
|!Type|!32/64|!32/32|!16/32|!16/16|
|byte| 8 |>|>|>|
|char([[*|Configurable 16 or 8 bit char type]])| 16 |>|>|>|
|short| 16 |>|>|>|
|int|32|32|16|16|
|long|64|32|32|16|
|float|32|32|16|16|
|double|64|32|32|16|
|boolean| 8 |>|>|>|>|

The used memory mode can be configured in the [[HaikuVM.properties]] file or as [[command line option|Command Line Options]].
[img[images/email.png]]

In papers and reports, please refer to ~HaikuVM as follows:
''Genom Bob. ~HaikuVM: a small JAVA VM for microcontrollers. http://haiku-vm.sourceforge.net/''
e.g. using the following ~BibTeX code:
{{{
@MISC{~HaikuVM,
        author = {Genom Bob},
        title = {~HaikuVM: a small JAVA VM for microcontrollers},
        howpublished = "\url{http://haiku-vm.sourceforge.net/}"
}
}}}
!Donors
Be the first who donate. I'm looking forward to get hardware to port ~HaikuVM on.

!Contributors
I wish to thank all the people that directly or indirectly contributed to the project:
*''Carl van Denzen'', worked on the leonardo port.
*''Alan'', worked on the gertboard port.
[[What is it?]]
[[News]]
<<tiddler [[Arduino]]>>
!Step 1 - Import from subversion repository at sourceforge 
After this step your eclipse IDE should show something like this:

[img[images/eclipse_step1.png]]

!Step 2 - Setup 'haiku' as external tool
Configure 'haiku.bat' (if on Windows) or 'haiku' (if on Linux) as external tool like this:

[img[images/eclipse_step2.png]]
-v ${file_prompt: a java file}

<<tiddler chmod>>
!Step 3 - Run external tool 'haiku'
When prompted pick a ~JAVA-file (for example 'Blink.java') in:
./haikuVM/examples/src/main/java/arduino/tutorial/Blink.java
Type the text for 'Exceptions'
''Q: Do I need the Arduino Uno Firmware on my ~ATMega328P or/and the Arduino IDE to run ~HaikuVM?''
''A:'' No, virtually everthing you need for ~HaikuVM comes with the download. (For Linux user see [[here|Linux]].) One critical point is the flash tool. If your device needs an other tool than avrdude, you have to download it from elsewhere.

''Q: All appears to go well, but the program doesn't appear to be running on the ~ATmega. It just sits there silently. Any idea?''
''A:'' I suggest to start with a basic and simple busy-wait example for AVR which you will find in './haikuVM/examples/src/main/java/avr/tutorial/~BlinkSimple.java' and is described in more detail [[here|BlinkSimple]]. 
Caution: First you have to edit and change it to your needs because this example assumes that the LED is on PORTB.
<code bash>
cd haikuVM/myCProject

/home/bob/haikuVM/bin/haikuc /home/bob/haikuVM/examples/src/main/java/avr/tutorial/BlinkSimple.java
/home/bob/haikuVM/bin/haikulink -v --Config simple010 -o BlinkSimple.hex /home/bob/haikuVM/examples/src/main/java/avr/tutorial/BlinkSimple.java
</code>

''Q: I'm trying to compile it in './bin/' with:
'./haiku -v - -Config arduino -o ~BlinkWithThread.hex ./~BlinkWithThread.java'
but have no success. Why?''
''A:'' Don't try it in ./bin/ and don't try it with relative pathes. Instead follow this wiki suggestions, move into ./haikuVM/myCProject and use absolute pathes like so:
<code bash>
cd haikuVM/myCProject

/home/bob/haikuVM/bin/haiku -v --Config simple010 -o BlinkSimple.hex /home/bob/haikuVM/examples/src/main/java/avr/tutorial/BlinkSimple.java
</code>


''Q: Is it possible to save the output of the command haiku into a trace file?''
''A:'' Yes, two ways I can think of:
<code bash>
c:\haikuVM\bin\haiku -v --Config simple010 -o BlinkSimple.hex C:\haikuVM\examples\src\main\java\avr\tutorial\BlinkSimple.java >std.out 2>std.err
or
c:\haikuVM\bin\haiku -v --Config simple010 -o BlinkSimple.hex C:\haikuVM\examples\src\main\java\avr\tutorial\BlinkSimple.java >std.outerr 2>&1
</code>

''Q: Is AVRISPMKII supported?''
''A:'' Not direct. You have to install libusbWin32 first. Then, when using 'usb' as port, has a chance to do the job.
<code bash>
c:\haikuVM\bin\haiku -v --Config simple010 --Config:Port usb -o BlinkSimple.hex C:\haikuVM\examples\src\main\java\avr\tutorial\BlinkSimple.java >std.out 2>std.err
</code>
 
''Q: Are interrupts enabled?''
''A:'' Yes, interrupts are enabled by default.

''Q: Is it possible to write my own interrupt routines?''
''A:'' Yes, see the tutorial about interrupts. Keep in mind that '~TIMER0_OVF_vect' interrupt is reserved for ~HaikuVM.

''Q: Is it possible to call a Java method from within a C function?''
''A:'' This is difficult.
#You need a Thread and a stack frame for the Java method.
#The method must be reachable for Java/~HaikuVM as well. (Otherwise it's optimized away.)

''Q: I want to change ~HaikuVM code (e.g. 'simpleOS.c'), what is the best place?''
''A:'' There are three answers:
#If your change is very project specific then './myCProject/haikuVM/simpleOS.c' is the best place.
#If the change is more general then './haikuVM/simpleOS.c' is the best place. But this will be overwritten with the download of the next ~HaikuVM version. 
#If the change is an enhancment of ~HaikuVM then send it to me or join the project as a developer.

''Q: The probem is, that avr-gcc needs include files (p.e. stdio.h).''
''A:'' 
#What's your avr-gcc version? The command 'avr-gcc -version' will print the current version. Compare this with commited versions [[here|Reported Usage]].
#Is your avr-gcc proper installed? Please, do an isolated test of avr-gcc with a simple ~HelloWorld.c program.

''Q: Is it possible to compile more than one Java program with ~HaikuVM and upload the HEX to arduino?''
''A:'' Compiling more than one Java program into one (third) program is not a question of ~HaikuVM but of Java programming. Consider this ''Program1'':
<code java>
package faqs.programs;
public class Program1 {
    public static void main(String[] args) {
        System.out.println("Hello ");
    }
}
</code>
and this ''Program2'':
<code java>
package faqs.programs;
public class Program2 {
    public static void main(String[] args) {
        System.out.println("World!");
    }
}
</code>
Both can be called from within this ''Program3'':
<code java>
package faqs.programs;
public class Program3 {
    public static void main(String[] args) {
        Program1.main(null);
        Program2.main(null);
    }
}
</code>
And may be compiled and uploaded like this:
<code bash>
mkdir \myPrograms
cd \myPrograms
C:\haikuVM\bin\haiku --Config duemilanove C:\haikuVM\examples\src\main\java\faqs\programs\Program3.java
</code>

''Q: Is it possible to compile against a JAR library with ~HaikuVM?''
''A:'' Again, this is not a question of ~HaikuVM but of Java skill. Take the example from above and put ''Program1'' and ''Program2'' into 'mylib.jar' or  use the prepared example comming with ~HaikuVM like this:
<code bash>
mkdir \myPrograms
cd \myPrograms
C:\HaikuVM\bin\haiku -v --Mode 16/32 --Config duemilanove -classpath C:\HaikuVM\lib\examples\mylib.jar C:\HaikuVM\examples\src\main\java\faqs\programs\Program3.java
</code>


''Q: How can I contribute to the project?''
''A:'' 
If you are a programmer and want to contribute code, ~HaikuVM is open-source and you are welcome to do so! Just send us your patches. There is no guarantee that your patch will be added to the upstream source, and all changes are carefully reviewed.

If you are not a programmer, but want to help out, feel free to look through the documentation or try installing ~HaikuVM and test it out. General editing, documentation contributions, and testing are always helpful.

''Q: How can I become an official member of the project?''
''A:'' 
The short answer is: "by being asked."

People are only added as official members of the ~HaikuVM project after their work has been proven. This usually means you will have contributed code in the form of patches before, or we know you from extensive testing work, or you frequently help with documentation, and we are impressed enough that we want you as part of the project.

All that said, you do not need to be a member of the project to help out. Feel free to contribute anything.

''Q: I think I've found a bug. How do I report it?''
''A:'' 
The project hosts a bug tracking here https://sourceforge.net/p/haiku-vm/tickets/. All bugs should be reported there as new tickets. This is also where you would request a new feature.

''Q: I need help! Where can I find some?''
''A:'' 
The project hosts forums at https://sourceforge.net/p/haiku-vm/discussion/general/. If you have a SourceForge username (or don't mind registering one), this is a good place to start.

If none of those options suffice, you can always email any of the project members directly. You will usually get a personal response, time permitting. 

''Q: How can I help ~HaikuVM?''
''A:'' I have multiple ideas open and you can work on any of them by joining as a developer. For example, 
* You can port ~HaikuVM on a PIC or ARM. 
* You can also help by fixing mistakes on this wiki-website 
* Improve the ~HaikuVM core. 
* Write a plugin for processing and its IDE. 
In short, I will appreciate any kind of help. So [[contact|Contact]] me now with your ideas for helping ~HaikuVM. Remember this project belongs to community and you. It will be a success only with your help and support. 

* Preemptive threads ([[More ...|Preemptive threads]])
* Exceptions ([[More ...|Exceptions]])
* Synchronization
* double and float support ([[More ...|double and float support]])
* Arrays, including multidimensional ones 
* Recursion 
* Garbage collection ([[More ...|Garbage collection]])
* Supports inheritance and interfaces
* Runs on AVR ~ATmega8, AVR ~ATmega328p (and Windows, UNIX) ([[More ...|Runs on AVR ATmega8, AVR ATmega328p (and Windows, UNIX)]])
* Configurable 64, 32 or 16 bit data types including [[half precision float]] ([[More ...|Configurable 64, 32 or 16 bit data types]]) 
* Configurable 16 or 8 bit type for char arrays ([[More ...|Configurable 16 or 8 bit char type]])
* Tested with Suns JAVA 1.6 and 1.7
* Zero Assembler Code ([[More ...|Zero Assembler Code]])
* Panic Support ([[More ...|Panic Support]])
* Compact: Requires only down to 5k Bytes of code memory which includes ~HaikuVM ''and'' your Java program. ([[More ...|Compact]])
* Fast: About 55k Java opcodes per second on 8 Mhz  AVR ~ATmega8 ([[More ...|Performance]])
* Needs only 250 Bytes RAM (the rest is for your JAVA application)
* Direct access to memory ([[More ...|Memory Access]])
* Partial support of JNI ([[More ...|Native JAVA Methods]])
* Direct access to C/C++ functions via annotations ''@~NativeCFunction'' and ''@~NativeCPPFunction''. ([[More ...|Tutorial JNI]])
* Uses a static linking model to reduce code footprint.
* Per-method dependency analyzer, that determines a set of methods that are really needed to run your application, so HaikuVM won't translate whole JAR files or class directories

!Limitations
* Does not support reflection (so, jRuby or Groovy are unlikely to run against ~HaikuVM)
* Does not call static class initializers in lazy order (instead they are all called eager just before your main method is called)
* Garbage collection without compaction
* No class loader support
* No object finalization support
* Array objects have no type information (and no typechecking in the bytecode handlers for Arrays)
* No weak references
* Interfaces partial supported
* No interrupt handlers may written in ~HaikuVM. Use JNI for this, see [[Tutorial Interrupts]].
~HaikuVM uses a simple mark & sweep conservative garbage collector (GC). I chosed this algorithm because of its simplicity. A downside is, that non-compacting collectors typically cause fragmentation on the heap. Another is, that the mark phase is usually implemented using recursion, which can potentially cause stack overflows. I therefore implemented a slower but non-recursive marking algorithm. Until now ~HaikuVM supports three types of ~GCs:
#No GC (no garbage collection at all) {{{GC=HAIKU_NoGC}}}
#Stop the world GC (default) {{{GC=HAIKU_ConservativGC}}}
#Incremental GC (slices of work of the GC are done between interpretation of bytecodes) {{{GC=HAIKU_IncrementalGC}}}
#Stop the world compacting GC (experimental) {{{GC=HAIKU_CompactingGC}}}
The GC mode can be configured in the [[HaikuVM.properties]] file or as [[command line option|Command Line Options]].
~HaikuVM at its core, is just another JAVA VM for micros (I began with ~AVRs). I decided to go without building an own JAVA runtime. Instead ~HaikuVM is tailor made to use the JAVA runtime coming with [[leJOS]]. ~HaikuVM works by compiling JAVA bytecode to C structs to be compiled by a C cross compiler for your target platform. So, the resulting code is small and fast. ([[More ...|Architecture]])

To produce an executable for a given target from a set of Java source files and libraries, three sets of tools are used:
*''JAVA tools''<br>A JAVA 6 compiler (or higher) and SDK from Oracle. ~HaikuVM is shipped with the leJOS runtime library. But you are invited to experiment with other runtime libraries as e.g. Oracle, ~OpenJDK or GNU Classpath. Any editor will do, but I recommend an Eclipse IDE to ease development and deployment. No matter what is the preferred development environment the outcome is a set of class files making up the application.
*''~HaikuVM tools''<br>These tools make up the core part of the ~HaikuVM environment. The outcome of the ~HaikuVM tools is a set of auto generated C files making up the C version of the application.The user points to the main entry point of the application (the main method) and the tools will now do two things:
**Compute the dependency extent of the main method (often called closure). This is the set of methods that may be executed as a result of running main, and the set of fields and other resources (e.g constants) that may be referenced. The tool will compute a conservative estimate of this set through a static analysis of the source code. The closure will contain both, code produced by the user and code extracted from referred libraries.
**Translate the closure into C code. The C code produced is basically a set of unsigned char arrays containing the byte code and a C representation of the constant pools. This C code can be thought of as a C version of the class files making up the dependency extent of the main method.
*''C/C++ tools''<br>These tools are the existing set of tools used by the embedded developer to translate C source code into uploadable hex files for the target. In many cases this will be some version of the GCC tool chain, but it may also be some other C tool chain. Using this C compiler the C source generated by the ~HaikuVM tools can be linked with the ~HaikuVM interpreter to produce the final executable for the target.

Software which you need:
#JAVA sdk 1.6 (or higher)
#[[download|https://sourceforge.net/projects/haiku-vm/files/downloads]] and unzip ~HaikuVM into C:\haikuVM
#Then haikufy, upload and run your JAVA Program on your Microcontroller.
Software the download includes:
#~HaikuVM tools
#[[leJOS]] runtime
#~WinAVR 20100110 (Windows C cross compiler for ~AVRs)
''Remark'': On LINUX you have to install a C cross compiler for ~AVRs by hand.

As an option I recommend the [[Eclipse IDE|Eclipse]] for development.
But using the [[Arduino IDE]] for Arduinos is supported as well.

~HaikuVM just should work out of the box. Unlike other JAVA ~VMs for microcontrollers it adapts automatically to the needs of your JAVA program. For example if your program don't uses doubles then bytecodes and C code for doubles are eliminated automatically. If your program don't uses multi-threading then bytecodes and C code for multi-threading are eliminated automatically. And so on. This means that virtually no fiddling with configurations is needed and memory consumption of ~HaikuVM is always squeezed down to the minimum.

Comments and questions are welcome ([[Contact]]). Keep in mind, this is still a work in progress, so there is more to come: both in terms of features and in terms of optimizations... 

!Getting started with a Duemilanove
Start with the following JAVA program (from the [[Tutorials]]).
<code java>
package arduino.tutorial;
import static haiku.avr.lib.arduino.WProgram.*;
public class Blink {
    static byte ledPin = 13;            // LED connected to digital pin 13

    public static void loop()           // run over and over again
    {
        digitalWrite(ledPin, HIGH);     // sets the LED on
        delay(1000);                    // waits for a second
        digitalWrite(ledPin, LOW);      // sets the LED off
        delay(1000);                    // waits for a second
    }

	public static void main(String[] args) {
        pinMode(ledPin, OUTPUT);        // sets the digital pin as output
        while(true) {
        	loop();
        }
    }
}
</code>
Haikufy, upload and run your JAVA Program on an ARDUINO like this:
<code bash>
cd C:\haikuVM\myCProject
C:\haikuVM\bin\haiku -v --Config duemilanove --Config:Port com5 C:\haikuVM\examples\src\main\java\arduino\tutorial\Blink.java
</code>
Assuming that your ARDUINO is connected on port com5. (The  Duemilanove is the reference system for ~HaikuVM.)
!Getting started with a Leonardo or Micro (or Duemilanove) using the Arduino IDE
Start with the following JAVA program (see [[Tutorials]]).
<code java>
package processing.examples._01_Basics;
import static processing.hardware.arduino.cores.arduino.Arduino.*;
public class Blink {
    static byte ledPin = 13;            // LED connected to digital pin 13

    public static void loop()           // run over and over again
    {
        digitalWrite(ledPin, HIGH);     // sets the LED on
        delay(1000);                    // waits for a second
        digitalWrite(ledPin, LOW);      // sets the LED off
        delay(1000);                    // waits for a second
    }

    public static void setup() {
        pinMode(ledPin, OUTPUT);        // sets the digital pin as output
    }
}
</code>
Haikufy your JAVA Program into your [[Arduino IDE]] like this:
<code bash>
cd C:\arduino-1.0.5\libraries
C:\haikuVM\bin\haiku -v --Config arduinoIDE C:\haikuVM\examples\src\main\java\processing\examples\_01_Basics\Blink.java
</code>
And upload it to your Leonardo with your [[Arduino IDE]]. ([[More...|Processing]])
!Getting started with others
Take a look into [[Reported Usage]] and follow the links.



//HaikuVM// - A Java VM for ARDUINO and other micros using the leJOS runtime.
These are some current configuration targets in ~HaikuVM.properties:
#pc
#unix
#arduino (default)
#arduinoIDE
#wiring
#duemilanove
#duemilanove.~ProcessingCLIB
#asuro
#nanovm
Some of this targets point to the same hardware (board) but different [[MicroKernels|Tutorial All About MicroKernels]] or ~OSs.

The file ~HaikuVM.properties is looked up in the following two pathes:
*<myCProject>\~HaikuVM.properties
*<~HaikuVM_HOME>\config\~HaikuVM.properties
If you follow the guidelines given here, then this will evaluate to:
*C:\haikuVM\myCProject\~HaikuVM.properties
*C:\haikuVM\config\~HaikuVM.properties
Many of the used properties of file '~HaikuVM.properties' may be overwritten in the command line and are explained here [[Command Line Options]].

The ~HaikuVM.properties may be inspected [[here|http://sourceforge.net/p/haiku-vm/code/HEAD/tree/trunk/config/HaikuVM.properties]] to find out how the targets above are covered with default values.
Let's proceed with an example using other Java types. Here the first native function should add an int, float and double. A second native function should deliver the result.
<code java>
package arduino.tutorial;

public class JNIenhanced {

    private static native void add(int a, float b, double c);
    private static native double result();
    
    public static void main(String[] args) {
        int a=3;
        float b=4;
        double c=5;
        
        add(a, b, c);
        System.out.println(a+" + "+b+" + "+c+" = "+result());
    }
}
</code>
Again copy the needed functions from 'haikuJNI.h' into file './myCProject/tutorial/~JNIenhanced.c'. And insert the intended code. You should come out with something similar like this:
<code cpp>
#include <jni.h>

static double result;
...
JNIEXPORT void Java_arduino_tutorial_JNIenhanced_add
  (JNIEnv *env, jclass obj, jint arg1, jfloat arg2, jdouble arg3)
{
    result = arg1 + arg2 + arg3;
}

...

JNIEXPORT jdouble Java_arduino_tutorial_JNIenhanced_result
  (JNIEnv *env, jclass obj)
{
    return result;
}
...
</code>

Come on, be brave and give it a try. The output is ''unexpected'':
{{{
3 + 4.0 + 5.0 = 17416.0
}}}
What's wrong here? Remember that in 16/32 mode (see [[Configurable 64, 32 or 16 bit data types]] and in [[half precision float]]) a Java float is a 16Bit data type and therefore is just a storage type. The AVR compiler does not support 16Bit floats. You have to use the right ~HaikuVM macros to unpack/pack float16 to something meaningful for AVR, as so:
<code cpp>
#include <jni.h>

static double result;
...
JNIEXPORT void Java_arduino_tutorial_JNIenhanced_add
  (JNIEnv *env, jclass obj, jint arg1, jfloat arg2, jdouble arg3)
{
    result = arg1 + TF2FLOAT(arg2) + TD2DOUBLE(arg3);
}

...

JNIEXPORT jdouble Java_arduino_tutorial_JNIenhanced_result
  (JNIEnv *env, jclass obj)
{
    return DOUBLE2TD(result);
}
...
</code>
Now we get the expected result:
{{{
3 + 4.0 + 5.0 = 12.0
}}}

As you can see in line 09 and 37, I was extra careful and used the unpack/pack macros for doubles, as well. Just to make this code more portable in case you want to give it a try in 16/16 memory mode.
I follow an example which I found here (http://journals.ecs.soton.ac.uk/java/tutorial/native1.1/implementing/field.html) and adapted it for ~HaikuVM.
 
First, the example Java code looks like this:
<code java>
package arduino.tutorial;

class JNI_FieldAccess {
    static int si;
    String s;

    private native void accessFields();

    public static void main(String args[]) {
        JNI_FieldAccess c = new JNI_FieldAccess();
        JNI_FieldAccess.si = 100;
        c.s = "abc";
        c.accessFields();
        System.out.println("In Java:");
        System.out.println("  FieldAccess.si = " + JNI_FieldAccess.si);
        System.out.println("  c.s = \"" + c.s + "\"");
    }
}
</code>

Second, the original JNI C code for the native method accessFields() looks like this (cut&pasted from the source referenced above):
<code C>
#include <stdio.h>
#include <jni.h>
#include "FieldAccess.h"

JNIEXPORT void JNICALL
Java_arduino_tutorial_JNI_FieldAccess_accessFields(JNIEnv *env, jobject obj)
{
  jclass cls = (*env)->GetObjectClass(env, obj);
  jfieldID fid;
  jstring jstr;
  const char *str;
  jint si;

  printf("In C:\n");

  fid = (*env)->GetStaticFieldID(env, cls, "si", "I");
  if (fid == 0)
    return;
  si = (*env)->GetStaticIntField(env, cls, fid);
  printf("  FieldAccess.si = %d\n", si);
  (*env)->SetStaticIntField(env, cls, fid, 200);

  fid = (*env)->GetFieldID(env, cls, "s", "Ljava/lang/String;");
  if (fid == 0)
    return;
  jstr = (*env)->GetObjectField(env, obj, fid);
  str = (*env)->GetStringUTFChars(env, jstr, 0);
  printf("  c.s = \"%s\"\n", str);
  (*env)->ReleaseStringUTFChars(env, jstr, str);

  jstr = (*env)->NewStringUTF(env, "123");
  (*env)->SetObjectField(env, obj, fid, jstr);
}
</code>

Third, for ~HaikuVM (since 1.2.3) the C code part has to be modified like this to work. And I assume that a char is only 1 byte long (see [[HaikuVM.properties]] Char = 1):
<code C>
#include <stdio.h>
#include <jni.h>

#include "../HaikuVM/utility/haikuConfig.h"
#include "../HaikuVM/utility/haikuJava.h"

JNIEXPORT void JNICALL
Java_arduino_tutorial_JNI_FieldAccess_accessFields(JNIEnv *env, jobject obj)
{
//jclass  cls = (*env)->GetObjectClass(env, obj);
  #define cls arduino_tutorial_JNI_FieldAccess
  jfieldID fid;
  jstring jstr;
  char *str;
  jint si;

  printf("In C:\n");

//fid = (*env)->GetStaticFieldID(env, cls, "si", "I");
  fid = (*env)->GetStaticFieldID(env, cls,  si , "I");
  if (fid == 0)
    return;
  si = (*env)->GetStaticIntField(env, cls, fid);
  printf("  FieldAccess.si = %d\n", si);
  (*env)->SetStaticIntField(env, cls, fid, 200);

//fid = (*env)->GetFieldID(env, cls, "s", "Ljava/lang/String;");
  fid = (*env)->GetFieldID(env, cls,  s , "Ljava/lang/String;");
  if (fid == 0)
    return;
  jstr = (*env)->GetObjectField(env, obj, fid);
  str = (*env)->GetStringUTFChars(env, jstr, 0);
  printf("  c.s = \"%s\"\n", str);
  (*env)->ReleaseStringUTFChars(env, jstr, str);

  jstr = (*env)->NewStringUTF(env, "123");
  (*env)->SetObjectField(env, obj, fid, jstr);
}

JNIEXPORT void native_arduino_tutorial_JNI_FieldAccess_accessFields_V(void) {
    pushTop();    // Save variable top onto stack.
    {
        jobject    obj = pop()->a;
        JNIEnv     *env = (JNIEnv*)&top;
        Java_arduino_tutorial_JNI_FieldAccess_accessFields(&env, obj);
    }
    popTop();
}
</code>

You see, the main difference comes from the fact, that ~HaikuVM needs to build the access to class 'arduino.tutorial.~JNI_FieldAccess' and fields 'si' and 's' during ''compile-time'' (si, s) and not during run-time ("si", "s").

I'm on my way to narrow the gap between the proprietary ~HaikuVM solution and the official JNI way. For now take it as it is.
In case you write some Java code which declares a ''native method'' like here:
<code java>
package arduino.tutorial;

public class JNIsimple {

    private static native int add(int a, int b);
    
    public static void main(String[] args) {
        int a=3;
        int b=4;
        System.out.println(a+" + "+b+" = "+add(a,b));
    }
}
</code>
~HaikuVM will detect this situation during the run of [[haikulink]] and writes JNI code templates and some wrapper code which is proprietary for ~HaikuVM, in your project directory file './myCProject/haikuC/haikuJNI.c'. In our case you will find something like this:
<code cpp>
...
/*
 * Class:     arduino.tutorial.JNIsimple
 * Method:    add
 * Signature: (II)I
 */
JNIEXPORT jint Java_arduino_tutorial_JNIsimple_add
  (JNIEnv *env, jclass obj, jint arg1, jint arg2)
{
    // TODO: insert your code here
    return 0;
}

/*
 * Proprietary HaikuVM stack to JNI interface function.
 * DO NOT EDIT THIS FUNCTION � it is machine generated.
 *
 * Class:     java.lang.System
 * Method:    getDataAddress
 * Signature: (Ljava/lang/Object;)I
 */
JNIEXPORT void native_arduino_tutorial_JNIsimple_add_III(void) {
    pushTop();	// Save variable top onto stack.
    {
        jint	arg2 = pop()->i;
        jint	arg1 = pop()->i;
        jobject	obj = NULL;
        JNIEnv *env = NULL;
        top.s1.i = Java_arduino_tutorial_JNIsimple_add(env, obj, arg1, arg2);
    }
    // Variable top holds the return value.
}
...
</code>
You have to copy this into some C file of your project directory. In case of this tutorial, do this in file './myCProject/tutorial/~JNIsimple.c'. The first function body '~Java_java_lang_System_getDataAddress' is the pure JNI function. The second function 'native_arduino_tutorial_~JNIsimple_add_III' is a proprietary ~HaikuVM function which just interfaces between the internal ~HaikuVM stack and the JNI function. Do not edit this function unless you know what you do. For the rest of this tutorial we will forget about the proprietary function(s) and will concentrate on the JNI functions.

Give life to your first JNI function by replacing the auto generated code (in file './myCProject/tutorial/~JNIsimple.c') by your semantic. In our case add arg1 and arg2.
<code cpp>
#include <jni.h>
...
JNIEXPORT jint Java_arduino_tutorial_JNIsimple_add
  (JNIEnv *env, jclass obj, jint arg1, jint arg2)
{
    return arg1 + arg2;
}
...
</code>
That's it! Now compile (by using haikulink) again and your native function will be used. Easy isn't it? (Don't forget to include 'jni.h', as can be seen in line 01.)

''Note''
~HaikuVM is a simple VM. When calling one of your JNI C functions the complete Haiku VM (that is every thread) is suspended. So keep in mind, that your JNI C functions have to be cooperative and lean.
Using functions from a C library is easy as 1,2,3 provided this library is included in your configuration. In this example we want to see the difference - if any - between the Java function Math.sin(x) and the C function sin(x) coming with C in the standard C library 'libm.a'. (Luckily 'libm.a' is included in virtual every [[HaikuVM.properties]] configuration.) Here is the Java code:
<code java>
package arduino.tutorial;

import haiku.vm.NativeCFunction;


public class JNINativeLIBC {

    private static native double sin(double a);
    
    public static void main(String[] args) {
        double x=2.1;
        System.out.println("Calculate sin("+x+")");
        System.out.println("This is the JAVA result: "+Math.sin(x));
        System.out.println("This is the libc result: "+sin(x));
    }
}
</code>
Again, you have to copy the automatic generated template in 'haikuJNI.c' into your own C file (let's say './myCProject/tutorial/~JNINativeLIBC.cpp') and add the call to sin(x). From the previous chapter you already learned to use the right ~HaikuVM macros to unpack/pack the values. At the end you should come out with some code like this which does the Job:
<code cpp>
...
JNIEXPORT jdouble Java_arduino_tutorial_JNINativeLIBC_sin
  (JNIEnv *env, jclass obj, jdouble arg1)
{
    return DOUBLE2TD(sin(TD2DOUBLE(arg1)));
}
...
</code>
This is pretty simple, isn't it?

Can we do much simpler? Yes, ~HaikuVM can! See [[here|JNI using functions from a C library using annotations]].
As you might have recognized [[here|JNI using functions from a C library]], interfacing to a C function is boilerplate code. ~HaikuVM can do this for you automatic. And you virtually will have no need to write C JNI code for this.

In this example I use sin(x) from the C math library of AVR and print the result side by side with the pure Java Math.sin(x). At the core, I just annotate the native method in question (here sin(double a)) with  ''@~NativeCFunction'' like so:
<code java>
package arduino.tutorial;

import haiku.vm.NativeCFunction;


public class JNINativeLIBC {

    @NativeCFunction
    private static native double sin(double a);
    
    public static void main(String[] args) {
        double x=2.1;
        System.out.println("Calculate sin("+x+")");
        System.out.println("This is the JAVA result: "+Math.sin(x));
        System.out.println("This is the libc result: "+sin(x));
    }
}
</code>
JNI functions annotated like this are generated into file './myCProject/haikuC/nativeCFunctions.cpp'.

As you might have expected, there is a similar annotation called ''@~NativeCPPFunction'' to refer to C++ functions.


BTW, if you want your own library to be included, use variable ''CLIBS'' of your configuration in [[HaikuVM.properties]]. For an example usage take a look at configuration 'leonardo.~UsingCLIB'.
This is how to let the examples, published in ''javamagazine'', run:

<code bash>
cd C:\haikuVM\myCProject
C:\haikuVM\bin\haiku -v --Config duemilanove C:\haikuVM\examples\src\main\java\de\javamagazin\Blink.java
</code>

<code bash>
cd C:\haikuVM\myCProject
C:\haikuVM\bin\haiku -v --Config duemilanove C:\haikuVM\examples\src\main\java\de\javamagazin\BlinkWithThread.java
</code>

<code bash>
cd C:\haikuVM\myCProject
C:\haikuVM\bin\haiku -v --Config duemilanove.UsingCLIB C:\haikuVM\examples\src\main\java\de\javamagazin\BlinkArduino.java
</code>

<code bash>
cd C:\haikuVM\myCProject
C:\haikuVM\bin\haiku -v --Config duemilanove.ProcessingCLIB C:\haikuVM\examples\src\main\java\de\javamagazin\BlinkProcessing.java
</code>

To let Leonardo talk to you, just enter the next two lines (assuming Leonardo is listening on port 32):
<code bash>
cd C:\haikuVM\myCProject
C:\haikuVM\bin\haiku -v --Config leonardo.UsingCLIB  --Config:Port com31  C:\haikuVM\examples\src\main\java\arduino\tutorial\HelloWorldProcessing.java
</code>

This solution variant uses a pre-compiled and pre-linked ~Arduino-Leonardo core library to have full access to USB.

After haikufying, the script continous and is ready to upload your code to the Leonardo, signaling it like this, to give yoe a chance to press the reset button:
<code bash>
read -t 6 -p "Please press the  R E S E T  button on the Leonardo"; avrdude -patmega32u4 -cavr109 -PCOM31 -b57600 ...
</code>

Now, it's all about timing. When you see this message you should immediatly press the reset button on the Leonardo. After about 6 seconds the Leonardo closes com32 and is ready for avrdude on com31. If the upload was successful avrdude will show somthing like this:
<code bash>
...
avrdude.exe: verifying ...
avrdude.exe: 9904 bytes of flash verified

avrdude.exe done.  Thank you.
</code>

As an alternative you might program your Leonardo with ~HaikuVM thru your [[Arduino IDE]].
!JAVA ~VMs
[[leJOS|http://en.wikipedia.org/wiki/LeJOS]] (and [[tinyVM|http://tinyvm.sourceforge.net/]])
[[NanoVM|http://www.harbaum.org/till/nanovm/index.shtml]] is a java virtual machine for the Atmel AVR ~ATmega8 CPU, the member of the AVR CPU family used e.g. in the DLR Asuro robot, manufactured by AREXX engineering. With the ~NanoVM, the Asuro can be programmed in the popular Java language.

[[TakaTuka:|http://takatuka.sourceforge.net/]] A Java Virtual Machine for Tiny Platforms. 
*For me it is an inspiring source of optimization of bytecodes itself.
[[Darjeeling|http://darjeeling.sourceforge.net/]] is a Virtual Machine (VM) for Micro Controller Units (MCU). It can execute a large subset of the Java language on 8- and 16-bit platforms, such as Atmega128 or ~MSP430. 

[[Squawk|http://en.wikipedia.org/wiki/Squawk_virtual_machine]] is a Java micro edition virtual machine for embedded system and small devices. I was surprised to see that ~HaikuVM shares similarities in:
*Threading and Synchronization. Synchronized methods and the use of the "synchronized" keyword generate explicit monitorenter/exit ~HaikuVM bytecodes. Unlike in Java, the "invoke" bytecodes never perform synchronization.
*Bytecode rewriting to squeeze the memory footprint.
[[Harissa|http://www.usenix.org/publications/library/proceedings/coots97/full_papers/muller/muller_html/node3.html]]: a compiler from Java bytecode to C
[[Toba|http://www.cs.arizona.edu/projects/sumatra/toba/doc/]]: A ~Java-to-C translator
[[Vishia|http://www.vishia.org/Java2C/]]:  java to C translator
[[jcgo|http://www.ivmaisoft.com/jcgo/demos.htm]]: a Java source to C code
[[jc|http://jcvm.sourceforge.net/]]
[[Soot|http://www.sable.mcgill.ca/soot/]]: a Java Optimization Framework
[[gnu classpath|http://www.gnu.org/software/classpath/stories.html]]
[[FLEX|http://flex.cscott.net/]] is a compiler infrastructure written in Java for Java
[[SlimVM|http://www.christianwimmer.at/Publications/Kerschbaumer09a/Kerschbaumer09a.pdf]]: A Small Footprint Java Virtual Machine for Connected Embedded Systems (loads JAVA Lib chunks on demand from a server)
[[dalvik|http://5963581449325967972-a-1802744773732722657-s-sites.googlegroups.com/site/io/dalvik-vm-internals/2008-05-29-Presentation-Of-Dalvik-VM-Internals.pdf?attachauth=ANoY7coivl317Iz9z-vk_afdBjSK6peZRoJRihQ9LLzPR3xEdKyZC7zToSfwFZfSCwsTFNtBp9x4UddWlIlExgrdGV0WIQFkHpXaBatDLur3GWnEV5HjS1k9EKJm_WmCHHPxYY0eEneX038ZcGdwUQi2dYvmGCReR2jBNykZbHkgJov1pfPT1uqz-HEd-3Rwef2x_al4ag5xZ43nsvwXjx5nVIi_I7Dx7MjXVBVrj1-gtoSojMlvv4a-qCyW4aa7PZVrsWzCOfDB&attredirects=0]]
[[jop|http://www.jopdesign.com/perf.jsp]] includes FPGA hardware: picoJAVA, femtoJAVA
[[bajos|http://code.google.com/p/bajos/wiki/FeaturesAndLimits]]
[[Javolution|http://javolution.org/]] real time JAVA
[[JNode|http://www.jnode.org/]]
[[uJ|http://dmitry.co/index.php?p=./04.Thoughts/11. uJ - a micro JVM]] Too big for an ~ATmega328p
[[KESO|http://www4.cs.fau.de/Research/KESO/]] To avoid the interpretation of bytecode on the target controllers, the Java bytecode is compiled to a native code binary image ahead of time. Based on OSEK/VDX -> no new Thread(), no exceptions ([[More ...|https://www4.cs.fau.de/Lehre/WS10/P_HOTSYS/Folien/07_KESO.pdf]])
Has an interesting concept of memory-mapped objects.
[[simpleRTJ|http://www.csc.uvic.ca/~mcheng/360/notes/simpleRTJ/]] "Specially optimized to run on the embedded systems with limited memory resources (from 48KB). On average the simpleRTJ will not require more than 18-23KB of RAM to run."
[[icelab HVM|http://icelab.dk/index.html]] Produces an executable for a given target from a set of Java source files and libraries.
~PreonVM (Virtenio) A VM for embedded systems and small devices.

http://en.wikipedia.org/wiki/List_of_Java_virtual_machines

!Other non-JAVA ~VMs
[[EmbedVM|http://www.clifford.at/embedvm/]] Very fast but supports only 8-bit and 16-bit data types, no floats.
[[SBI|http://evprojects.altervista.org/projects/sbi/]] Assembler-like syntax.
[[AmForth|http://sourceforge.net/projects/amforth/]] is an easily extendible command interpreter for the Atmel ~AVR8 Atmega micro controller family. It has a turnkey feature for embedded use too.
[[Forth|http://www.avrfreaks.net/index.php?module=Freaks%20Academy&func=viewItem&item_id=626&item_type=project]] other older project.
[[occam-pi:|http://concurrency.cc/]] An IDE uploads your native OCCAM code to a web service running in the Amazon VM cloud. This service compiles it into downloadable bytecode for a so called TVM which is running on your Arduino.

!Miscellaneous
[[ProGuard|http://proguard.sourceforge.net/]]
~ProGuard is a free Java class file shrinker, optimizer, obfuscator, and preverifier. It detects and removes unused classes, fields, methods, and attributes. It optimizes bytecode and removes unused instructions.

!Creative and inspiring
*[[SWIG|http://www.swig.org/Doc1.3/Java.html#imclass]] integration with C++ objects.
*Memory Access: http://www.kdgregory.com/index.php?page=java.byteBuffer
My Linux is UBUNTU 12.04 LTS. And this is what I did as some user 'bob'.
After downloading of haikuVM into '/home/bob/haikuVM' I had to do minor preparation:
<code bash>
# I changed some shell scripts to have execute permission
chmod +x haikuVM/bin/*

# Sorry some scripts may still have '\r\n' instead of '\n' only
dos2unix haikuVM/bin/*

# I found that javac and the AVR tool chain was missing on my UBUNTU
sudo apt-get install openjdk-6-jdk
sudo apt-get install gcc-avr binutils-avr gdb-avr avr-libc avrdude

# I plugged in my ARDUINO Duemilanove and found out that it came on /dev/ttyUSB0
ls -ltr /dev
#sudo usermod -aG dialout bob # does not work for me
sudo chmod a+rw /dev/ttyUSB0
ls -ltr /dev/ttyUSB0
</code>
''Important Note 1''
Until now I have reported success for gcc-avr 4.5.1 and 4.5.3. But no success with 4.6.2.

I then had to modify [[HaikuVM.properties]] to adapt to '/dev/ttyUSB0' by changing this two lines for arduino:

<code bash>
...
arduino.Port = /dev/ttyUSB0
arduino.Upload = avrdude -pm328p -cstk500v1 -P$(HAIKU_PORT) -b57600 -Uflash:w:$(HAIKU_OUTPUT):a
...
</code>
Finally, I first proceeded step by step:
<code bash>
cd haikuVM/myCProject

/home/bob/haikuVM/bin/haikuc /home/bob/haikuVM/examples/src/main/java/arduino/tutorial/BlinkWithThread.java
/home/bob/haikuVM/bin/haikulink -v --Config arduino -o BlinkWithThread.hex /home/bob/haikuVM/examples/src/main/java/arduino/tutorial/BlinkWithThread 
/home/bob/haikuVM/bin/haikuupload BlinkWithThread.hex
</code>
Then I did it again but now, as an alternative, with a one-liner:
<code bash>
/home/bob/haikuVM/bin/haiku -v --Config arduino -o BlinkWithThread.hex /home/bob/haikuVM/examples/src/main/java/arduino/tutorial/BlinkWithThread
</code>
''Important Note 2''
Before you call any of these scripts mentioned above (haikuc, haikulink, haikuupload or haiku) make sure you are in an empty directory! Any empty directory will work, but I suggest to move (cd) into the prepared directory 'haikuVM/myCProject' which comes with the download.
Version 1.2.3
[[GettingStarted]]
[[Features]]
[[Release Notes]]
[[Command Line Options]]
[[Wish List]]
[[Code Size|Compact]]
[[Speed|Performance]]
[[Support|http://sourceforge.net/p/haiku-vm/tickets/]]
[[Arduino]]
[[Processing]]
[[Asuro Robot|Asuro]]
[[leJOS]]
[[Download|https://sourceforge.net/projects/haiku-vm/files/latest/download]]
[[Tutorials]]
[[Reported Usage]]
[[FAQ]]
[[Porting]]
[[Contributors]]
[[Sourceforge]]
[[Links]]
[[Contact]]
When it comes to microcontroller programming it is often necessary to have direct access to memory and microcontroler registers. Although against the spirit of JAVA but, having methods for memory access is convenient. ~HaikuVM supports two different techniques to access memory:
#Classic: ~HaikuVM offers native getter and setter methods to access memory.
#Annotational: ~HaikuVM allows to annotate static fields as ''@~NativeCVariable#''
!Classic: Getters and Setters
~HaikuVM offers native getter and setter methods to access memory.
<code java>
package haiku.vm;
public class MemoryAccess {
    public static native void   setMemory8(int adr, int int8);
    public static native void   setMemory16(int adr, int int16);
    public static native int    getMemory8(int adr);
    public static native int    getMemory16(int adr);
    
    ...
}
</code>
Armed with this set of methods and if you know the wanted memory addresses, it's easy to read out e.g. analog data from an ~ATmega8, without being forced to fall back to C code:
<code java>
    ...
    public static final long F_CPU   = 8000000L;
    public static final int REFS0    = 6;
    public static final int ADSC     = 6;
    public static final int ADIF     = 4;
    public static final int ADC      = (((0x04) + 0x20)); //16Bit
    public static final int ADCSRA   = (((0x06) + 0x20));
    public static final int ADMUX    = (((0x07) + 0x20));
    ...

    public static int ReadADC(int mux) {
        setMemory8(ADMUX, (1 << REFS0) | mux);              // voltage reference with external capacity
        setMem(ADCSRA, (1 << ADSC));                        // start the AD conversion

        while ((getMemory8(ADCSRA) & (1 << ADIF)) == 0)     // wait for the end of the AD conversion
            ;

        return getMemory16(ADC);                            // read 16Bit result
    }
</code>
Remark: It's not always easy to find out the proper addresses which are needed for the getter and setter methods.
!Annotational
Static variables annotated with ''@~NativeCVariable#'' (where # is one of 8, 16, 32 or 64) are directly mapped to (equal named and existing) C Variables. So ~HaikuVM will not allocate memory for this variables in the JAVA static memory space.
The example given for the 'Classic' technique may now be rewritten like this:
<code java>
    ...
    public static final long F_CPU  = 8000000L;
    public static final int REFS0   = 6;
    public static final int ADSC    = 6;
    public static final int ADIF    = 4;
    @NativeCVariable16 
    public static volatile int ADC;
    @NativeCVariable8 
    public static volatile int ADCSRA;
    @NativeCVariable8 
    public static volatile int ADMUX;
    ...

    public static int ReadADC(int mux) {
        ADMUX =  (1 << REFS0) | mux;            // voltage reference with external capacity
        ADCSRA |= (1 << ADSC);                  // start the AD conversion

        while ((ADCSRA & (1 << ADIF)) == 0)     // wait for the end of the AD conversion
            ;

        return ADC;                             // read 16Bit result
    }
</code>
Here the variables ADC, ADCSRA and ADMUX (with exactly this names) have to exist in the underlying C code or libraries. (This condition is fullfilled for AVR projects because this variables are declared somewhere in include files given for ~AVRs.)

Using this technique allows you to copy&past many C examples to JAVA.

I have to mention a common pitfall. Reading a 8Bit C variable into a JAVA int variable is possible. ~HaikVM handles the incoming 8Bit C value as a (signed) byte type which causes the sign to be propagated to the int. If this is not what you want then mask with 0xff. Like shown in the following snippet from a Two Wire module:
<code java>
    ...
    public static final int TWEA = 0x06;
    public static final int TWINT = 0x07;
    public static final int TWEN = 0x02;
    @NativeCVariable8 
    public static volatile int TWCR;
    @NativeCVariable8 
    public static volatile int TWDR;
    ...

    static int i2c_read_byte() {  
        TWCR = (1 << TWINT) | (1 << TWEA) | (1 << TWEN); // start data reception, transmit ACK  
        while (((TWCR & (1 << TWINT))==0));  
        return TWDR & 0xff; // mask with 0xff to unmask sign
    }  
</code>
!A Word of Warning
#The size of ~HaikuVM JAVA types like int and long depends on your [[Memory Mode|Configurable 64, 32 or 16 bit data types]]. Where the introduced memory access methods (see above) don't depend on this. For example, if you call getMemory16(..) the result is always truncated to 16 Bit independent of your selected [[Memory Mode|Configurable 64, 32 or 16 bit data types]]. In other words, type sizes of ~HaikuVM JAVA variables and C variables are independent.
#Native C variables are out of scope for the garbage collector. This means, be extra careful if you store object pointers into C variables.

!~HaikuVM Objects
Let's start by comparing two class definitions. The first one is a C struct, the second one is Java. They both declare the same member variables, with (mostly) the same types, the C struct describes the layout of a block of memory and ~HaikuVM tries to mimic this as close as possible (in contrast a classic Java class typically doesn't). The idea is to make the mapping to C as close as possible to simplify implementation and improve execution speed.
<code C>
struct {
  unsigned int x;
  unsigned int y;
} Coordinate;
</code>
<code Java>
class Coordinate {
  int x;
  int y;
}
</code>
In fact, ~HaikuVM maps this Java object to memory by generating a C typedef like this:
<code C>
struct {
  jint x;
  jint y;
} Coordinate;
</code>
In ~HaikuVM, objects are pointers to this memory structures.

~HaikuVM does not use the C heap and malloc(..) is not used to allocate memory for Java objects. Instead ~HaikuVM uses its own ~GCalloc(..) function to place Java objects on its own heap and puts meta information (memory size and Java class) just before this object memory layout. One way to express meta information plus object layout in C might look like this.
<code C>
typedef struct {
  jheapsize allocsize;
  jclass clazz;
  struct {
    jint x;
    jint y;
  } Coordinate;
} CoordinateWithHaikuVMOverhead;
</code>
Where
*''allocsize'' is the memory size in bytes including bytes needed for this header.
*''clazz'' is a pointer to the (flash) memory where the class of this object is described. See ''~HaikuVM Classes'' below.
In addition the most significant bit of ''allocsize'' is used to mark an object in the mark phase of [[garbage collection|Garbage collection]].
!~HaikuVM Array Objects
For example a Java array of N doubles 
<code Java>
  new double[N];
</code>
is dynamic mapped into heap memory like this:
<code C>
typedef struct {
  jheapsize allocsize;  // memory size is in bytes and including bytes needed for this header
  jclass clazz;
  struct {
    jint length;
    jdouble array[N];
  } jdoubleArrayMem;
} ADoubleArrayWithHaikuVMOverhead;
</code>
In C it's possible to place an already sized array into a struc.
<code C>
struct {
  int data[10];
} Data;
</code>
This isn't possible in ~HaikuVM. If you write this in Java:
<code Java>
class Data {
  int[] data= new int[10];
};
</code>
~HaikuVM will do something similar like this during compile time:
<code C>
typedef struct {
  jheapsize allocsize;
  jclass clazz;
  struct {
    jobject data;
  } Data;
} DataWithHaikuVMOverhead;
</code>
Where ''data'' is a pointer to a Java array object. Then the Java array object is allocated like this during run time:
<code C>
typedef struct {
  jheapsize allocsize;
  jclass clazz;
  struct {
    jint length;
    jint array[10];
  } jintArrayMem;
} AnIntArrayWithHaikuVMOverhead;
</code>
And the memory address of '~AnIntArrayWithHaikuVMOverhead.jintArrayMem' is assigned to (the C pointer) '~DataWithHaikuVMOverhead.Data.data' .
!~HaikuVM Classes
In ~HaikuVM a class definition is placed in flash memory (and not on the Java heap). Its layout is expressed like this:
<code C>
typedef struct class_t {
  const struct class_t * superClass;  // pointer to superclass (this class extends superClass)
  const jheapsize mem;                // size of object in bytes
  const uint8_t size;                 // length of msg2meth[]
  const msg2meth_t msg2meth[];        // msgIdx -> meth for every virtual method
} class_t;
</code>
And ''msg2meth'' is a direct C array (not a pointer to an array) with ''size'' entries. Containing the list of all (local) virtual Java methods of a class. Each array element looks like this:
<code C>
typedef struct {
  const uint8_t msgIdx;
  const ByteCode * meth;
} msg2meth_t;
</code>
Where ''msgIdx'' is the global unique message index (representing the signature of a method) of this virtual method and ''meth'' is a pointer to the bytecode of the [[method body|Compact HaikuVM Code]].

!References
I recommend to read the very good article on this site http://www.kdgregory.com/index.php?page=java.byteBuffer
For example currentTimeMillis() is defined as ''native'' in java.lang.System:
<code java>
package java.lang;
...
public class System {
...
    /**
     * Returns the current time in milliseconds.
     * This is the number of milliseconds since the AVR has been on.
     */
    public static native long currentTimeMillis();
...
}
</code>

~HaikuVM produces the following snippet in file ./haikuC/haikuJNI.c for you.
<code c>
/*
 * Class:     java.lang.System
 * Method:    currentTimeMillis
 * Signature: ()J
 */
JNIEXPORT jlong Java_java_lang_System_currentTimeMillis
  (JNIEnv *, jclass);

JNIEXPORT jlong Java_java_lang_System_currentTimeMillis
  (JNIEnv *env, jclass obj)
{
    // TODO: insert your code here
    return 0;
}

/*
 * Proprietary HaikuVM stack to JNI interface function.
 * DO NOT EDIT THIS FUNCTION � it is machine generated.
 * 
 * Class:     java.lang.System
 * Method:    currentTimeMillis
 * Signature: ()J
 */
JNIEXPORT void native_java_lang_System_currentTimeMillis_J(void) {
    pushTop();    // Save variable top onto stack.
    {
        jclass     obj = NULL;
        JNIEnv     *env = NULL; // not used in HaikuVM
        top.j = Java_java_lang_System_currentTimeMillis(env, obj);
    }
    // Variable top holds the return value. But we have to push the lower half.
    pushTop0();
}
</code>
In this case C function //native_java_lang_~System_currentTimeMillis_J(void)// is the interface between the proprietary ~HaikuVM stack layout and the plain JNI C method //~Java_java_lang_System_currentTimeMillis(~JNIEnv *env, jobject obj)// which finally has to implement the basic functionality.

So, file ./haikuC/haikuJNI.c is a good resource for your C function templates because ~HaikuVM produces a snippet for ''every'' native JAVA method found in your program. Ist a better solution than using the native method C file generator: ''javah.exe'' which ships with the SDK. Because it bridges the gap between JNI and the proprietary ~HaikuVM stack layout by generating //native_...(..)// C functions as well.

See also [[Tutorial JNI]].
!!2014/11/16: Improved this dokumnet.
*A new chapter about [[Porting]].
*A new chapter about [[Memory Layout of HaikuVM Objects]]
!!2014/11/06: Version 1.2.3 is released.
*Improved this HTML documentation.
*JNI support is very close to the standard [[JNI field access]]
*New support for ARDUINO IDE 1.5.8
**New support for ARDUINO Micro. Based on Leonardo support.
**Re-newed support for ARDUINO Leonardo
!!2014/07/24: Version 1.2.2 is released.
!!2014/04/12: Tested ~HaikuVM 1.2.2 with JAVA 8
* Now ~HaikuVM runs with JAVA 1.8.0_05.
!!2014/04/03: ~HaikuVM runs on an Attiny45
* For programming the Attiny45 in JAVA/~HaikuVM with the Arduino IDE, I followed this tutorial: http://highlowtech.org/?p=1695 <br>Then I wrote [['BlinkAttiny45.java'|https://sourceforge.net/p/haiku-vm/code/HEAD/tree/trunk/examples/src/main/java/processing/examples/_01_Basics/BlinkAttiny45.java]] - which blinks a LED on Pin 0 - as a proof of concept. Sadly, only 90 Bytes are left (out of 256 ~ATTiny45 RAM) for the JAVA/~HaikuVM heap.
!!2014/03/01: Version 1.2.1 is released.
* Fixed minor configuration odds.
!!2014/01/20: Version 1.2.0 is released.
* Better and inovative Panic Support using an extra panic room (if configured) on the heap. ([[More ...|Panic Support]])
!!2013/11/26
* I tested the Yún successfully with ~HaikuVM and [[Arduino IDE]]! (Since some days I'm the proud owner of a Yún.)
!!2013/11/16: Version 1.1.1 is released.
* Enabled ~HaikuVM for JAVA 7.
* Integration with Arduino IDE 1.5 (and Arduino Due).
* Checked against many tests coming from [[Darjeeling|http://darjeeling.sourceforge.net/]] (or ~TakaTuka?)
!!2013/10/23
* Added a [[Wish List]].
!!2013/10/20: Version 1.1.0 is released.
*Reshaped JAVA object layout (structs) to support seamless integration with native C structs.<br> See this wonderful explanation in [[The Organization of Objects|http://www.kdgregory.com/index.php?page=java.byteBuffer]] to understand the problem behind the sceens.
!!2013/09/27: Support for the Arduino IDE
*See here [[Arduino IDE]]
!!2013/08/21: More complete documentation
*New Tutorial [[JNI field access]]
*Enhanced [[Tutorial Blink]]
*Enhanced [[Tutorial JNI]]
!!2013/08/04: Version 1.0.4 is released.
If you want to test ~HaikuVM but you don't have a microcontroller, here are two ways to get your first impression:
*Support for Windows as target. ([[More ...|Visual Studio]])
*Support for Ubuntu as target. ([[More ...|Ubuntu]])
!!2013/07/14: Version 1.0.3 is released.
Including examples given for an article in ''javamagazine''. ([[More ...|Javamagazine Examples]])
Full support for Leonardo. ([[More ...|Leonardo]])
Annotations ''@~NativeCFunction'' and ''@~NativeCPPFunction'' to refer seamless to given C/C++ functions. ([[More ...|Tutorial JNI]])
!!2013/03/03: Version 1.0.2 is released. 
Including a tutorial about JNI. ([[More ...|Tutorials]])
!!2013/02/09: Better Linux support. 
Tested on UBUNTU 12.04 LTE. ([[More ...|Linux]])
!!2013/01/01: Single line command interface
Enter one line to compile, upload and run your JAVA program (let's say '~BlinkWithThread') to an Arduino connected on port com5:
<code bash>
cd haikuVM\myCProject
C:\haikuVM\bin\haiku -v --Config arduino --Config:Port com5 -o BlinkWithThread.hex C:\haikuVM\examples\src\main\java\arduino\tutorial\BlinkWithThread.java
</code>
Or Linux:
<code bash>
cd haikuVM/myCProject
/home/bob/haikuVM/bin/haiku -v --Config arduino --Config:Port /dev/ttyUSB0 /home/bob/haikuVM/examples/src/main/java/arduino/tutorial/BlinkWithThread.java 
</code>

!!2013/01/01: Direct access to memory and microcontroller registers
Static fields annotated with ''@~NativeCVariable#'' (where # is one of 8, 16, 32 or 64) are directly mapped to (equal named and existing) C variables. ([[More ...|Memory Access]])
<code java>
    ...
    public static final int UDRE0 = 5;
    @NativeCVariable8 // tells HaikuVM to map UCSR0A to a 8Bit C variable called UCSR0A 
    public static volatile int UCSR0A;
    @NativeCVariable8 // tells HaikuVM to map UDR0 to a 8Bit C variable called UDR0
    public static volatile int UDR0;
    ...
    public void write(int b) {
        while ( (UCSR0A & (1 << UDRE0)) == 0 ) /*poll*/ ;
        UDR0=b;
    };
</code>
Most of the code written for microcontrollers was originally written in C. This direct access to memory technique allows you to virtually copy&past this to JAVA.

During runtime, ~HaikuVM is able to check for odd JVM conditions and react on this with so called "panic". In a full blown ~HaikuVM one of the following 10 exceptions are thrown by the JVM, corresponding to the reason of panic:
*~ArithmeticException
*~ArrayIndexOutOfBoundsException
*~ArrayStoreException
*~ClassCastException
*~IndexOutOfBoundsException
*~NoSuchMethodError
*~NullPointerException
*~OutOfMemoryError
*~StackOverflowError
*~VirtualMachineError
But for a microcontroller a full blown panic support might be overkill with respect to the given resources. ~HaikuVM gives you the chance to configure and even program your needs.
!Mode: No Panic Support
For having no panic support at all set the following configuration ([[read more about configuration ...|HaikuVM.properties]])
*~PanicSupport = 0
*~PanicExceptions = 0x0
No C/C++ code for any panic condition is included in the ~HaikuVM (~PanicExceptions = 0x0).
If any of this conditions will occur during runtime, your program is likely to crash. On the other hand, in this mode, the ~HaikuVM code is very dense and, because all runtime panic checks are missing, the fastest code possible.
There is no need for your panic handler and therefore it is not included (~PanicSupport = 0).
Configure this mode if your program is tested very well and you don't expect any panic condition to appear during runtime.

!Mode: Simple Panic Support
For having simple panic support set the following configuration
*~PanicSupport = 0
*~PanicExceptions = <list some exceptions here>
A reasonable setting could be this:
*~PanicExceptions = ~NullPointerException | ~NoSuchMethodError | ~OutOfMemoryError | ~ClassCastException
C/C++ code for the selected panic conditions is included in the ~HaikuVM.
If any of this conditions will occur during runtime, ~HaikuVM will detect this, will ''not'' throw any exception on this (because ~PanicSupport = 0) but will unwind the runtime stack for the current thread and will ''continue'' execution in the main(..) or run() method.
There is no need for your panic handler and therefore it is not included (~PanicSupport = 0).

!Mode: Flexible Panic Support
For having flexible or full blown panic support set the following configuration
*~PanicSupport = 1
*~PanicExceptions = <list some exceptions here>
A full blown setting is this:
*~PanicExceptions = ~NullPointerException | ~ArrayStoreException | ~IndexOutOfBoundsException | ~NoSuchMethodError | ~StackOverflowError | ~OutOfMemoryError | ~ClassCastException | ~ArrayIndexOutOfBoundsException | ~VirtualMachineError | ~ArithmeticException
or for short:
*~PanicExceptions = 0xffff
C/C++ code for the selected panic conditions is included in the ~HaikuVM.
If any of this conditions will occur during runtime, ~HaikuVM will detect this and will call ''your'' written Java method panic(..) with the following panic values:
|~HaikuVM Panic Value|Intended exception to be thrown|
| 2 |~NullPointerException|
| 4 |~ArrayStoreException|
| 8 |~IndexOutOfBoundsException|
| 16 |~NoSuchMethodError|
| 32 |~StackOverflowError|
| 64 |~OutOfMemoryError|
| 128 |~ClassCastException|
| 256 |~ArrayIndexOutOfBoundsException|
| 512 |~VirtualMachineError|
| 1024 |~ArithmeticException|
What really happens in the body of panic(..) is up to you. The only thing ~HaikuVM does is, when in ~StackOverflowError-panic or ~OutOfMemoryError-panic, to set field panicRoom=null with the intention to release potential panicRoom memory to let your panic(..) method have some room to execute, even in a panic conditions triggered by short memory. If this does not help (e.g. panicRoom space was to low to support full panic(..) execution) ~HaikuVM falls back to ''Simple Panic Support''.

A running example of a panic(..) method can be seen in ''[[haiku.vm.MicroKernel|http://sourceforge.net/p/haiku-vm/code/HEAD/tree/trunk/bootstrap/src/main/java/haiku/vm/MicroKernel.java]]''. Just overwrite this code to change the behavior to your needs.
!General
The former Java virtual machines (which are Java virtual machines without ~HotSpot technique), which simply interpreted bytecodes one at a time, were clocked at 30 to 50 times slower than natively compiled C++. Just-in-time (JIT) compilers have narrowed the performance gap to 3 to 10 times slower than C++. Current Java virtual machines come with ~HotSpot technique, which makes them par with or better then natively compiled C++ [[[1]|http://www.artima.com/designtechniques/hotspot.html]].

~HaikuVM is a Java virtual machine, which simply interpretes bytecodes one at a time. So don't expect miracles in speed.
 

!Performance of ~HaikuVM (Revision 52)
The performance test was made on an ''Atmega328p'' 16Mhz with the following JAVA program:
<code java>
public class Fibonacci32Bit {
  static int fib(int n) {
    if(n < 2)
      return 1;
    else
      return fib(n-2) + fib(n-1);
  }

  public static void main(String[] args) {
    long t0 = System.currentTimeMillis();
    for(int i=0;i<=30;i++)
      System.out.println("Fibonacci of "+i+" is "+fib(i)+" in "+(System.currentTimeMillis()-t0)+" ms");
  }
}
</code>

The program was compiled, linked und uploaded as follows:
<code bash>
C:\haikuVM\bin\haiku --Config arduino --Mode 32/64 C:\haikuVM\haikuBench\src\main\java\haikuvm\bench\Fibonacci32Bit
</code>
During cross compiling with ~WinAVR 20100110 the optimization level was set for size: -Os
Result:
<code bash>
Fibonacci of 0 is 1 in 73 ms
Fibonacci of 1 is 1 in 127 ms
Fibonacci of 2 is 2 in 194 ms
Fibonacci of 3 is 3 in 261 ms
Fibonacci of 4 is 5 in 326 ms
Fibonacci of 5 is 8 in 391 ms
Fibonacci of 6 is 13 in 458 ms
Fibonacci of 7 is 21 in 535 ms
Fibonacci of 8 is 34 in 610 ms
Fibonacci of 9 is 55 in 694 ms
Fibonacci of 10 is 89 in 787 ms
Fibonacci of 11 is 144 in 888 ms
Fibonacci of 12 is 233 in 1010 ms
Fibonacci of 13 is 377 in 1167 ms
Fibonacci of 14 is 610 in 1369 ms
Fibonacci of 15 is 987 in 1653 ms
Fibonacci of 16 is 1597 in 2046 ms
Fibonacci of 17 is 2584 in 2633 ms
Fibonacci of 18 is 4181 in 3538 ms
Fibonacci of 19 is 6765 in 4934 ms
Fibonacci of 20 is 10946 in 7133 ms
Fibonacci of 21 is 17711 in 10643 ms
Fibonacci of 22 is 28657 in 16259 ms
Fibonacci of 23 is 46368 in 25300 ms
Fibonacci of 24 is 75025 in 39851 ms
Fibonacci of 25 is 121393 in 63353 ms
Fibonacci of 26 is 196418 in 101303 ms
Fibonacci of 27 is 317811 in 162640 ms
Fibonacci of 28 is 514229 in 261832 ms
Fibonacci of 29 is 832040 in 422249 ms
Fibonacci of 30 is 1346269 in 681731 ms
</code>
So this JAVA program running with ~HaikuVM Revision 52 needed ''681731 ms'' for fib(30). ([[Compare with results from newer revisions.|Performance History]])


!!Compared with plain C running on ARDUINO Duemilanove

This is the competing C program for fib(30):
<code c>
int32_t fib(int32_t n) {
	if(n < 2) 
	  return 1;
	else
	  return fib(n-2) + fib(n-1);
} 

int main() {
	int32_t i;
	long t0 = millis();
	for(i=0;i<=30;i++) {
          printf("Fibonacci of %ld is %ld in %ld ms\n", i, fib(i), (long)(millis()-t0));
	}
	return 0;
}
</code>
This C program, again compiled with ~WinAVR 20100110 -Os (optimize for size), needed ''19494 ms'' and compiled with -O3 (optimize for speed) needed ''16825 ms''.

Conclusion: This (specific) JAVA program runnning with ~HaikuVM is a ''factor 35 (or 41) slower'' than the corresponding plain C program.

!!Compared with leJOS

Because ~HaikuVM is not ported on NXJ (until now), I had to compare it in an indirect way. For this I put a question about performance into the leJOS forum ([[see ...|http://lejos.sourceforge.net/forum/viewtopic.php?f=7&t=2989&p=14800&hilit=performance#p14800]]).

Thankfully I got this answer:
"Anyway it turns out that ~RobotC like NXC does not support recursion so the fib test is not looking like a good test case. But I ran it anyway in Java the total time taken for up to and including fib 30 is ''197566'', the same code in gcc based C takes ''3432ms'', so the native C code in this instance is 57 times faster."

So there is a chance that ~HaikuVM would be faster than leJOS by a factor of 1,6 (or 1,4). But this comparision must be taken with care.

!!Compared with JAVA 1.6 under Windows XP 32Bit
The program was compiled and linked as follows:
<code bash>
haiku -target WIN32 -r Fibonacci32Bit
</code>
I used the Microsoft Visual C++ 2005 compiler. The final runtime was ''1204 ms'' on my computer.

Pure JAVA 1.6 needed ''656 ms''. To be fair I ran it in pure interpreter mode like this:
<code bash>
java -Xint Fibonacci32Bit
</code>

Conclusion: ~HaikuVM is about a factor of 2 slower than pure JAVA (interpreting). Not bad for an application not using assembler and using a data alignment set to 1 byte.
 
Because I was curious I ran it with JAVA 1.6 Hotspot and it needed only ''47ms'' for fib(30) on my computer.



Cross compiled with ~WinAVR 20100110 the optimization level was set for size: -Os
!Revision 232 fib(30)
Program:   19656 bytes (60.0% Full)
Data:       1834 bytes (89.6% Full)
<code bash>
Fibonacci of 0 is 1 in 87 ms
Fibonacci of 1 is 1 in 147 ms
Fibonacci of 2 is 2 in 207 ms
Fibonacci of 3 is 3 in 268 ms
Fibonacci of 4 is 5 in 331 ms
Fibonacci of 5 is 8 in 392 ms
Fibonacci of 6 is 13 in 459 ms
Fibonacci of 7 is 21 in 527 ms
Fibonacci of 8 is 34 in 597 ms
Fibonacci of 9 is 55 in 672 ms
Fibonacci of 10 is 89 in 755 ms
Fibonacci of 11 is 144 in 863 ms
Fibonacci of 12 is 233 in 976 ms
Fibonacci of 13 is 377 in 1117 ms
Fibonacci of 14 is 610 in 1282 ms
Fibonacci of 15 is 987 in 1508 ms
Fibonacci of 16 is 1597 in 1839 ms
Fibonacci of 17 is 2584 in 2316 ms
Fibonacci of 18 is 4181 in 3023 ms
Fibonacci of 19 is 6765 in 4126 ms
Fibonacci of 20 is 10946 in 5855 ms
Fibonacci of 21 is 17711 in 8580 ms
Fibonacci of 22 is 28657 in 12938 ms
Fibonacci of 23 is 46368 in 19941 ms
Fibonacci of 24 is 75025 in 31202 ms
Fibonacci of 25 is 121393 in 49355 ms
Fibonacci of 26 is 196418 in 78669 ms
Fibonacci of 27 is 317811 in 126030 ms
Fibonacci of 28 is 514229 in 202598 ms
Fibonacci of 29 is 832040 in 326417 ms
Fibonacci of 30 is 1346269 in 526701 ms
</code>
!Revision 180 fib(30)
Program:   19636 bytes (59.9% Full)
Data:       1834 bytes (89.6% Full)
<code bash>
Fibonacci of 0 is 1 in 99 ms
Fibonacci of 1 is 1 in 163 ms
Fibonacci of 2 is 2 in 229 ms
Fibonacci of 3 is 3 in 293 ms
Fibonacci of 4 is 5 in 354 ms
Fibonacci of 5 is 8 in 420 ms
Fibonacci of 6 is 13 in 484 ms
Fibonacci of 7 is 21 in 562 ms
Fibonacci of 8 is 34 in 636 ms
Fibonacci of 9 is 55 in 713 ms
Fibonacci of 10 is 89 in 815 ms
Fibonacci of 11 is 144 in 912 ms
Fibonacci of 12 is 233 in 1026 ms
Fibonacci of 13 is 377 in 1181 ms
Fibonacci of 14 is 610 in 1360 ms
Fibonacci of 15 is 987 in 1598 ms
Fibonacci of 16 is 1597 in 1943 ms
Fibonacci of 17 is 2584 in 2432 ms
Fibonacci of 18 is 4181 in 3173 ms
Fibonacci of 19 is 6765 in 4312 ms
Fibonacci of 20 is 10946 in 6084 ms
Fibonacci of 21 is 17711 in 8912 ms
Fibonacci of 22 is 28657 in 13429 ms
Fibonacci of 23 is 46368 in 20669 ms
Fibonacci of 24 is 75025 in 32314 ms
Fibonacci of 25 is 121393 in 51088 ms
Fibonacci of 26 is 196418 in 81401 ms
Fibonacci of 27 is 317811 in 130386 ms
Fibonacci of 28 is 514229 in 209579 ms
Fibonacci of 29 is 832040 in 337641 ms
Fibonacci of 30 is 1346269 in 544781 ms
</code>
Some words on porting to other platforms. First, you will find some pre-configurate targets in [[HaikuVM.properties]]. For new platforms you have to keep this in mind:
!Data Alignment
Currently ~HaikuVM needs a data alignment of 1 byte on all platforms.
*win-avr: ''-fpack-struct''
*gcc: ''-fpack-struct=1''
*visual C:  ''-Zp1''

!Delete unused Code and Data
Some compilers can be command to keep code size and data size small by deleting unused functions and data. Which is of some importance on small micro controllers.
*win-avr: ''-ffunction-sections -fdata-sections''
*gcc: ''- -gc-sections''
~HaikuVM implements effective quasi-preemptive thread scheduling with atomic JVM instructions. 

~HaikuVM is preemptive on bytecode level not on machine instruction Level.  (That's why I call it quasi-preemptive.) As a consequence every bytecode is executed atomar (and so are all native methods). ~HaikuVM supports thread synchronization with the Java ''synchronized'' keyword. In contrast to some other implementations monitor counters are not stored in the object headers but rather live in a separate construct to further save space. (Because in a microcontroller the vast majority of objects will never act as monitors.)

Timeslicing is done by performing a context switch on schedule-instructions which are selected bytecodes and specific native methods. Schedule-instructions are:
* branch bytecodes (either backward or forward)
* any invoke* bytecode (e.g. invokestatic)
* any *return bytecode (e.g. ireturn)
* Thread.yield()
* Thread.sleep(..)
* Thread.join()
* wait(..)
* synchronized methods or synchronized blocks
This is how to program virtual any Arduino in JAVA using the processing habit (not using main() but setup() and loop()), library and the [[Arduino IDE]] to let the LED blink.
<code java>
package processing.examples._01_Basics;

import static processing.hardware.arduino.cores.arduino.Arduino.*;

public class Blink {
    static byte ledPin = 13;            // LED connected to digital pin 13

    public static void loop()           // run over and over again
    {
        digitalWrite(ledPin, HIGH);     // sets the LED on
        delay(1000);                    // waits for a second
        digitalWrite(ledPin, LOW);      // sets the LED off
        delay(1000);                    // waits for a second
    }

    public static void setup() {
        pinMode(ledPin, OUTPUT);        // sets the digital pin as output
    }
}
</code>
<hr>
<<tiddler [[Arduino IDE]]>>

A big part of the ''wiring core library'' is ported to JAVA. For the rest help is wanted.
!Version 1.2.3 (Revision: 604) (Date: 2014/11/05)
#Support for Arduino IDE 1.5.8.
#Put more user friendly information into the closure process.
#Bug fixed: When using C keyword 'const' in conjunction with 'PROGMEM' with new AVR compiler.
!Version 1.2.2 (Revision: 590) (Date: 2014/07/24)
#Crash fixed: When accessing double fields (~GETFIELD_D) ~HaikuVM crashed.
#Bug fixed: When declaring multidimensional array fields, C code declarations for this arrays were generated wrong.
#Bug fixed: When called with a user defined JAR file. (See [[FAQ]]s)
!Version 1.2.1 (Revision: 571) (Date: 2014/03/01)
#Bug fixed: When running for target PC 'make.exe' wasn't found in PATH if used in Visual Studio Console.
!Version 1.2.0 (Revision: 557) (Date: 2014/01/20)
#Bug fixed: instanceOf now returns ''false'' if obj==null
#Bug fixed: now a class is included, even if only referenced by byte codes "checkcast" or "instanceof".
#Bug fixed: when handling fields using generic types.
#Enhanced: Added more basic tests (still not all are passing)
#Enhanced: Having undefined virtual methods resulting in message: "%s [%d] was never declared!" will not stop haikufying any more. Instead a severe warning is given.
#Enhanced: If a method is included into the application image I added a (indexed) reason why it was included (is in the closure). Just to debug complex situations.
#Enhanced: makefile now better for UNIX (and WINDOWS?)
#Enhanced: less C warnings
#Enhanced: automated ~JUNITs for linux
#Renamed: from throwException() to panic(int exceptionCode, int exceptionArg)
#Renamed: configuration options ([[More ...|Panic Support]])
##~InternalExceptionEnable into ~PanicExceptions
##~InternalExceptionThrow into ~PanicSupport
#Nicer message: "Looking for '~HaikuVM.properties' in path: .."
!Version 1.1.1 (Revision: 542) (Date: 2013/11/17)
#Bug fixed: With byte codes ~I2B, ~I2S and BIPUSH.
#Bug fixed: Which prevented any change of the configuration (more or less). (Thank you Carl.)
#Enhanced Nullpointer hardening.
#Support for ~ArithmeticException.
#Getting more OS independent with put/getchar.
#Support for int16_t/int32_t agnostic Integer and Long classes.
#Tuned for UNIX.
!Version 1.1.0 (Revision: 510) (Date: 2013/10/26)
#Support for Arduino IDE 1.5.4 (and ''Arduino Due'' compiles at least. Feedback wanted.)!!!
#Reshaped JAVA object layout (structs) to support seamless integration with native C structs.
#Bug fixed: When path to JAVA contains spaces. (Thank you Carl.)
#Bug fixed: When compiled for Leonardo.
#Bug fixed: now cleans up before each new cross compilation.
!Version 1.0.5 (Revision: 483) (Date: 2013/09/27)
#Support for the [[Arduino IDE]] 1.0.5
!Version 1.0.4 (Revision: 444) (Date: 2013/08/04)
#Bug fixed: jint putchar(int) -> int putchar(int)
#Using ''$(~HAIKU_LINKER)'' to access any linker. Which in turn supported MS Visual Studio.
#Support for ~WIN32 / X86 target.
#Windows: use %TEMP%\haikuvm as target for *.class files.
#Used more canonicalPathes (which makes traces easier to read).
#Allows relative class names.
#~NativeCVariableEnhanced.c uses now only C features (not C++ features)
!Version 1.0.3 (Revision: 434) (Date: 2013/07/14)
#Better error messages.
#Enhanced usability.
#Arduino Leonardo is supported (including serial io). ([[More ...|Leonardo]])
#New configuration variable ''~TimerInterrupt'' to enable ISR for timing.
#Support for annotational [[Memory Access]] of your own C variables. ([[More ...|Tutorial JNI]])
#Enhanced JNI Support:
##Support of cpp files.
##Using ''$(~HAIKU_CC)'' and ''$(~HAIKU_CXX)'' instead of constants avr-gcc and avr-g++.
##Closer to javah Output.
##Support for C library access.
#Stricter C(++) syntax.
#Annotations @~NativeCFunction and @~NativeCPPFunction for more seamless JNI support
!Version 1.0.2 (Revision: 311) (Date: 2013/03/03)
#Bug fixed: ldc() for ints (~LDC_I) stored an int at wrong place in top.
#Bug fixed: now C #includes follow JAVA nested static scopes.
#JNI is now prepared to go public. ([[More ...|Tutorial JNI]])
#Correct millisecond timing now works for a wider range of Mz. ([[More ...|Tutorial Timing]])
#Bug fixed: Stdout and Stderr of shell commands were merged characterwise.
#Linux: No need for dos2unix any more.
!Version 1.0.1 (Revision: 285) (Date: 2013/02/11)
#Bug fixed: synchronized method failed if it had more then one RETURN.
#Entering com ports is more homogen between Windows and Linux now.
!Version 1.0.0 (Revision: 277) (Date: 2013/02/09)
#Better Linux support. ([[More ...|Linux]])
#Less C compiler warnings during cross compile phase
#~JUnits for many major features
#Basic AVR tutorial
!Version 0.9.5 (Revision: 258) (Date: 2013/01/01)
#Support for annotational [[Memory Access]]
#Support for numeric constrains for adapt to Memory models (~DBL_CNSTR, ~FLT_CNSTR, ~LONG_CNSTR, ~INT_CNSTR)
#First (remote) ~JUnit
#Bug fixed: Support for synchronized non-void methods
#Bug fixed: a quote in a String "'" is now supported.
#Less cross compiler warnings.
!Version 0.9.4 (Revision: 232) (Date: 2012/12/02)
#~WinAVR 20100110 included in download
#Support for arduino-1.0.2
#[[haiku]] command now supports {{{--Config:Port <port>}}}
#Reduced compiler warnings
#Moved available() and read() to ~HardwareSerial.
#Added AVR Two Wire constants
*OS
**[[Windows|Visual Studio]]
**[[UBUNTU 12.04 LTS; 12.10|Ubuntu]]
**[[Mac OS X Mountain Lion|http://backsite.wordpress.com/2013/02/28/java-fur-arduino-und-andere-mcs-mit-haikuvm/]]
*Microcontroller
**[[ATmega328p|Duemilanove]]
**[[Atmega8|Asuro]]
**Atmega16
*Platforms
**[[Arduino]]
***[[Yún|Arduino IDE]]
***[[Duemilanove]]
***[[Leonardo]]
***[[Micro|Arduino IDE]]
***[[UNO SMD R2|http://backsite.wordpress.com/2013/02/28/java-fur-arduino-und-andere-mcs-mit-haikuvm/]]
**[[ASURO|Asuro]]
**NIBOBEE
**Gertboard
*Software
**Java
***oracle jdk1.6.0
***java 7 (32 and 64)
***java 8 (jdk1.8.0_05) 
**Compiler
***gcc
****4.6.3 (compare with avr-gcc 4.6.2 which has a reported failure)
***Microsoft Compiler
****VS 2005
****VS 2008
****VS 2010
**Crosscompiler
***avr-gcc
****4.5.1
****4.5.3
****4.3.3 (~WinAVR 20100110)
**** (4.6.2 has a reported failure)
****4.8.2
**Flash Tools
***avrdude
***~ASUROFlash155
***~Nibobee-Programmer
**~IDEs
***Eclipse (Indigo, Kepler R1)
***Arduino IDE (1.0.5, 1.5.4, 1.5.8)
~HaikuVM is successfully testet against the following targets (and some more):
#AVR
## ~ATmega8 ([[More ...|Asuro]])
## ~ATmega328p ([[More ...|Arduino]])
## ~ATmega32u4 ([[More ...|Leonardo]])
#Windows XP (32Bit) ([[More ...|Visual Studio]])
#Windows 2008 R2 (64Bit) ([[More ...|Visual Studio]])
#UNIX (Ubuntu 64Bit) ([[More ...|Ubuntu]])
A Java VM for ARDUINO and other micros using the leJOS runtime.
//HaikuVM//
[[Summary|http://sourceforge.net/projects/haiku-vm/]]
[[Download|https://sourceforge.net/projects/haiku-vm/files/downloads/]]
Subversion [[RO|https://sourceforge.net/p/haiku-vm/code/]] [[HTTPS|https://svn.code.sf.net/p/haiku-vm/code/trunk]]

See also:
[[Discussion|https://sourceforge.net/p/haiku-vm/discussion/general/]]
[[Tickets|https://sourceforge.net/p/haiku-vm/tickets/milestones]]
Each stack object has a variable called 'length' and consists of length stack slots. A stack slot has the size of a jint or jobject (void* in C), what ever needs more bytes ([[see|Configurable 64, 32 or 16 bit data types]]). As usual for ~JVMs ~HaikuVM uses two slots if it stores a long or a double on the stack. ~HaikuVM does not try to save stack space by using only part of a slot (eg. to store a byte).

|N-1| possible unused |
|..|~|
|..|~|
|61|bgcolor(#6f9): frame 3 |
|..|~|
|..|~|
|35|~|
|34|bgcolor(#6f9): frame 2 |
|..|~|
|21|~|
|20|bgcolor(#6f9): frame 1 |
|..|~|
|..|~|
|2|~|
|1|bgcolor(#66b): previous stack |
|0|bgcolor(#66b): last stack pointer |
| |bgcolor(#66b): length = N |
| initial stack segment |c

|M-1| possible unused |
|..|~|
|..|bgcolor(#6f9): frame |
|..|~|
|2|~|
|1|bgcolor(#66b): previous stack |
|0|bgcolor(#66b): last stack pointer |
| |bgcolor(#66b): length = M |
| contiguous stack segment |c

Where 
* N is [[InitialMainThreadStackSize|HaikuVM.properties]], if it's the first stack segment for the main thread.
* N is [[InitialOtherThreadStackSize|HaikuVM.properties]], if it's the first stack segment for any other thread.
* M is the maximum stack (size + 2*2) needed for the frame of a called function. For example if javac calculated a max. need for 20 stack slots (including call arguments and local variables) then M=20+2*2. (Ok, I lied. But not realy, just to simplyfy. This is only true for a 16 Bit architecture. On a 32 Bit architecture this morphes to M=20+2*4. Because there a *void has a size of 4 byte. More general: M=20+2*sizeof(*void).)

Each thread has its own stack queue. This queue is a one directional linked list, connected via 'previous stack'. Each function call (per thread) allocates its own frame on ist thread stack. To save space, function frames do overlap (where ever possible).

|21| function stack |
|..|~|
|9|~|
|8|bgcolor(#68b): last program counter |
|7|bgcolor(#68b): previous frame |
|6|bgcolor(#6fa): local2 |
|5|~|
|4|bgcolor(#6fa): local1 |
|3|bgcolor(#6f9): arg3 |
|2|bgcolor(#6f9): arg2 |
|1|bgcolor(#6f9): arg1 |
|0|bgcolor(#6f9): object |
| frame layout |c
.tiddler {padding:1em 1em 0;  font-size:1.2em;border-bottom-style:solid; border-width:5px;border-color:#04b; 
font-family: "Verdana",Arial,sans-serif;
line-height: 1.4em;
}
.viewer pre {padding:0.5em; margin-left:0.5em; font-size:.9em; line-height:0.9em; overflow:auto;}
div.tiddler .subtitle {font-size: 7pt;}
h1,h2,h3,h4,h5,h6 {
    #color:[[ColorPalette::Foreground]]; 
    background:transparent;
    color: rgb(32, 74, 135);
    font-family: "Verdana",Arial,sans-serif;
    #font-family: "Georgia","Times New Roman",serif;
}
.title {
    #color:[[ColorPalette::Foreground]];
    line-height: 120%;
    color: rgb(32, 74, 135);
    font-family: "Verdana",Arial,sans-serif;
    #font-family: "Georgia","Times New Roman",serif;
}  
[[StyleSheetSyntaxHighlighter]]
/*{{{*/
body {background:[[ColorPalette::Background]]; color:[[ColorPalette::Foreground]];}

a {color:[[ColorPalette::PrimaryMid]];}
a:hover {background-color:[[ColorPalette::PrimaryMid]]; color:[[ColorPalette::Background]];}
a img {border:0;}

h1,h2,h3,h4,h5,h6 {color:[[ColorPalette::SecondaryDark]]; background:transparent;}
h1 {border-bottom:2px solid [[ColorPalette::TertiaryLight]];}
h2,h3 {border-bottom:1px solid [[ColorPalette::TertiaryLight]];}

.button {color:[[ColorPalette::PrimaryDark]]; border:1px solid [[ColorPalette::Background]];}
.button:hover {color:[[ColorPalette::PrimaryDark]]; background:[[ColorPalette::SecondaryLight]]; border-color:[[ColorPalette::SecondaryMid]];}
.button:active {color:[[ColorPalette::Background]]; background:[[ColorPalette::SecondaryMid]]; border:1px solid [[ColorPalette::SecondaryDark]];}

.header {background:[[ColorPalette::PrimaryMid]];}
.headerShadow {color:[[ColorPalette::Foreground]];}
.headerShadow a {font-weight:normal; color:[[ColorPalette::Foreground]];}
.headerForeground {color:[[ColorPalette::Background]];}
.headerForeground a {font-weight:normal; color:[[ColorPalette::PrimaryPale]];}

.tabSelected {color:[[ColorPalette::PrimaryDark]];
	background:[[ColorPalette::TertiaryPale]];
	border-left:1px solid [[ColorPalette::TertiaryLight]];
	border-top:1px solid [[ColorPalette::TertiaryLight]];
	border-right:1px solid [[ColorPalette::TertiaryLight]];
}
.tabUnselected {color:[[ColorPalette::Background]]; background:[[ColorPalette::TertiaryMid]];}
.tabContents {color:[[ColorPalette::PrimaryDark]]; background:[[ColorPalette::TertiaryPale]]; border:1px solid [[ColorPalette::TertiaryLight]];}
.tabContents .button {border:0;}

#sidebar {}
#sidebarOptions input {border:1px solid [[ColorPalette::PrimaryMid]];}
#sidebarOptions .sliderPanel {background:[[ColorPalette::PrimaryPale]];}
#sidebarOptions .sliderPanel a {border:none;color:[[ColorPalette::PrimaryMid]];}
#sidebarOptions .sliderPanel a:hover {color:[[ColorPalette::Background]]; background:[[ColorPalette::PrimaryMid]];}
#sidebarOptions .sliderPanel a:active {color:[[ColorPalette::PrimaryMid]]; background:[[ColorPalette::Background]];}

.wizard {background:[[ColorPalette::PrimaryPale]]; border:1px solid [[ColorPalette::PrimaryMid]];}
.wizard h1 {color:[[ColorPalette::PrimaryDark]]; border:none;}
.wizard h2 {color:[[ColorPalette::Foreground]]; border:none;}
.wizardStep {background:[[ColorPalette::Background]]; color:[[ColorPalette::Foreground]];
	border:1px solid [[ColorPalette::PrimaryMid]];}
.wizardStep.wizardStepDone {background:[[ColorPalette::TertiaryLight]];}
.wizardFooter {background:[[ColorPalette::PrimaryPale]];}
.wizardFooter .status {background:[[ColorPalette::PrimaryDark]]; color:[[ColorPalette::Background]];}
.wizard .button {color:[[ColorPalette::Foreground]]; background:[[ColorPalette::SecondaryLight]]; border: 1px solid;
	border-color:[[ColorPalette::SecondaryPale]] [[ColorPalette::SecondaryDark]] [[ColorPalette::SecondaryDark]] [[ColorPalette::SecondaryPale]];}
.wizard .button:hover {color:[[ColorPalette::Foreground]]; background:[[ColorPalette::Background]];}
.wizard .button:active {color:[[ColorPalette::Background]]; background:[[ColorPalette::Foreground]]; border: 1px solid;
	border-color:[[ColorPalette::PrimaryDark]] [[ColorPalette::PrimaryPale]] [[ColorPalette::PrimaryPale]] [[ColorPalette::PrimaryDark]];}

.wizard .notChanged {background:transparent;}
.wizard .changedLocally {background:#80ff80;}
.wizard .changedServer {background:#8080ff;}
.wizard .changedBoth {background:#ff8080;}
.wizard .notFound {background:#ffff80;}
.wizard .putToServer {background:#ff80ff;}
.wizard .gotFromServer {background:#80ffff;}

#messageArea {border:1px solid [[ColorPalette::SecondaryMid]]; background:[[ColorPalette::SecondaryLight]]; color:[[ColorPalette::Foreground]];}
#messageArea .button {color:[[ColorPalette::PrimaryMid]]; background:[[ColorPalette::SecondaryPale]]; border:none;}

.popupTiddler {background:[[ColorPalette::TertiaryPale]]; border:2px solid [[ColorPalette::TertiaryMid]];}

.popup {background:[[ColorPalette::TertiaryPale]]; color:[[ColorPalette::TertiaryDark]]; border-left:1px solid [[ColorPalette::TertiaryMid]]; border-top:1px solid [[ColorPalette::TertiaryMid]]; border-right:2px solid [[ColorPalette::TertiaryDark]]; border-bottom:2px solid [[ColorPalette::TertiaryDark]];}
.popup hr {color:[[ColorPalette::PrimaryDark]]; background:[[ColorPalette::PrimaryDark]]; border-bottom:1px;}
.popup li.disabled {color:[[ColorPalette::TertiaryMid]];}
.popup li a, .popup li a:visited {color:[[ColorPalette::Foreground]]; border: none;}
.popup li a:hover {background:[[ColorPalette::SecondaryLight]]; color:[[ColorPalette::Foreground]]; border: none;}
.popup li a:active {background:[[ColorPalette::SecondaryPale]]; color:[[ColorPalette::Foreground]]; border: none;}
.popupHighlight {background:[[ColorPalette::Background]]; color:[[ColorPalette::Foreground]];}
.listBreak div {border-bottom:1px solid [[ColorPalette::TertiaryDark]];}

.tiddler .defaultCommand {font-weight:bold;}

.shadow .title {color:[[ColorPalette::TertiaryDark]];}

.title {color:[[ColorPalette::SecondaryDark]];}
.subtitle {color:[[ColorPalette::TertiaryDark]];}

.toolbar {color:[[ColorPalette::PrimaryMid]];}
.toolbar a {color:[[ColorPalette::TertiaryLight]];}
.selected .toolbar a {color:[[ColorPalette::TertiaryMid]];}
.selected .toolbar a:hover {color:[[ColorPalette::Foreground]];}

.tagging, .tagged {border:1px solid [[ColorPalette::TertiaryPale]]; background-color:[[ColorPalette::TertiaryPale]];}
.selected .tagging, .selected .tagged {background-color:[[ColorPalette::TertiaryLight]]; border:1px solid [[ColorPalette::TertiaryMid]];}
.tagging .listTitle, .tagged .listTitle {color:[[ColorPalette::PrimaryDark]];}
.tagging .button, .tagged .button {border:none;}

.footer {color:[[ColorPalette::TertiaryLight]];}
.selected .footer {color:[[ColorPalette::TertiaryMid]];}

.error, .errorButton {color:[[ColorPalette::Foreground]]; background:[[ColorPalette::Error]];}
.warning {color:[[ColorPalette::Foreground]]; background:[[ColorPalette::SecondaryPale]];}
.lowlight {background:[[ColorPalette::TertiaryLight]];}

.zoomer {background:none; color:[[ColorPalette::TertiaryMid]]; border:3px solid [[ColorPalette::TertiaryMid]];}

.imageLink, #displayArea .imageLink {background:transparent;}

.annotation {background:[[ColorPalette::SecondaryLight]]; color:[[ColorPalette::Foreground]]; border:2px solid [[ColorPalette::SecondaryMid]];}

.viewer .listTitle {list-style-type:none; margin-left:-2em;}
.viewer .button {border:1px solid [[ColorPalette::SecondaryMid]];}
.viewer blockquote {border-left:3px solid [[ColorPalette::TertiaryDark]];}

.viewer table, table.twtable {border:2px solid [[ColorPalette::TertiaryDark]];}
.viewer th, .viewer thead td, .twtable th, .twtable thead td {background:[[ColorPalette::SecondaryMid]]; border:1px solid [[ColorPalette::TertiaryDark]]; color:[[ColorPalette::Background]];}
.viewer td, .viewer tr, .twtable td, .twtable tr {border:1px solid [[ColorPalette::TertiaryDark]];}

.viewer pre {border:1px solid [[ColorPalette::SecondaryLight]]; background:[[ColorPalette::SecondaryPale]];}
.viewer code {color:[[ColorPalette::SecondaryDark]];}
.viewer hr {border:0; border-top:dashed 1px [[ColorPalette::TertiaryDark]]; color:[[ColorPalette::TertiaryDark]];}

.highlight, .marked {background:[[ColorPalette::SecondaryLight]];}

.editor input {border:1px solid [[ColorPalette::PrimaryMid]];}
.editor textarea {border:1px solid [[ColorPalette::PrimaryMid]]; width:100%;}
.editorFooter {color:[[ColorPalette::TertiaryMid]];}
.readOnly {background:[[ColorPalette::TertiaryPale]];}

#backstageArea {background:[[ColorPalette::Foreground]]; color:[[ColorPalette::TertiaryMid]];}
#backstageArea a {background:[[ColorPalette::Foreground]]; color:[[ColorPalette::Background]]; border:none;}
#backstageArea a:hover {background:[[ColorPalette::SecondaryLight]]; color:[[ColorPalette::Foreground]]; }
#backstageArea a.backstageSelTab {background:[[ColorPalette::Background]]; color:[[ColorPalette::Foreground]];}
#backstageButton a {background:none; color:[[ColorPalette::Background]]; border:none;}
#backstageButton a:hover {background:[[ColorPalette::Foreground]]; color:[[ColorPalette::Background]]; border:none;}
#backstagePanel {background:[[ColorPalette::Background]]; border-color: [[ColorPalette::Background]] [[ColorPalette::TertiaryDark]] [[ColorPalette::TertiaryDark]] [[ColorPalette::TertiaryDark]];}
.backstagePanelFooter .button {border:none; color:[[ColorPalette::Background]];}
.backstagePanelFooter .button:hover {color:[[ColorPalette::Foreground]];}
#backstageCloak {background:[[ColorPalette::Foreground]]; opacity:0.6; filter:alpha(opacity=60);}
/*}}}*/
/*{{{*/
* html .tiddler {height:1%;}

body {font-size: .75em; font-family:arial,helvetica; margin:0; padding:0;}

h1,h2,h3,h4,h5,h6 {font-weight:bold; text-decoration:none;}
h1,h2,h3 {padding-bottom:1px; margin-top:1.2em;margin-bottom:0.3em;}
h4,h5,h6 {margin-top:1em;}
h1 {font-size:1.35em;}
h2 {font-size:1.25em;}
h3 {font-size:1.1em;}
h4 {font-size:1em;}
h5 {font-size:.9em;}

hr {height:1px;}

a {text-decoration:none;}

dt {font-weight:bold;}

ol {list-style-type:decimal;}
ol ol {list-style-type:lower-alpha;}
ol ol ol {list-style-type:lower-roman;}
ol ol ol ol {list-style-type:decimal;}
ol ol ol ol ol {list-style-type:lower-alpha;}
ol ol ol ol ol ol {list-style-type:lower-roman;}
ol ol ol ol ol ol ol {list-style-type:decimal;}

.txtOptionInput {width:11em;}

#contentWrapper .chkOptionInput {border:0;}

.externalLink {text-decoration:underline;}

.indent {margin-left:3em;}
.outdent {margin-left:3em; text-indent:-3em;}
code.escaped {white-space:nowrap;}

.tiddlyLinkExisting {font-weight:bold;}
.tiddlyLinkNonExisting {font-style:italic;}

/* the 'a' is required for IE, otherwise it renders the whole tiddler in bold */
a.tiddlyLinkNonExisting.shadow {font-weight:bold;}

#mainMenu .tiddlyLinkExisting,
	#mainMenu .tiddlyLinkNonExisting,
	#sidebarTabs .tiddlyLinkNonExisting {font-weight:normal; font-style:normal;}
#sidebarTabs .tiddlyLinkExisting {font-weight:bold; font-style:normal;}

.header {position:relative;}
.header a:hover {background:transparent;}
.headerShadow {position:relative; padding:4.5em 0 1em 1em; left:-1px; top:-1px;}
.headerForeground {position:absolute; padding:4.5em 0 1em 1em; left:0; top:0;}

.siteTitle {font-size:3em;}
.siteSubtitle {font-size:1.2em;}

#mainMenu {position:absolute; left:0; width:10em; text-align:right; line-height:1.6em; padding:1.5em 0.5em 0.5em 0.5em; font-size:1.1em;}

#sidebar {position:absolute; right:3px; width:16em; font-size:.9em;}
#sidebarOptions {padding-top:0.3em;}
#sidebarOptions a {margin:0 0.2em; padding:0.2em 0.3em; display:block;}
#sidebarOptions input {margin:0.4em 0.5em;}
#sidebarOptions .sliderPanel {margin-left:1em; padding:0.5em; font-size:.85em;}
#sidebarOptions .sliderPanel a {font-weight:bold; display:inline; padding:0;}
#sidebarOptions .sliderPanel input {margin:0 0 0.3em 0;}
#sidebarTabs .tabContents {width:15em; overflow:hidden;}

.wizard {padding:0.1em 1em 0 2em;}
.wizard h1 {font-size:2em; font-weight:bold; background:none; padding:0; margin:0.4em 0 0.2em;}
.wizard h2 {font-size:1.2em; font-weight:bold; background:none; padding:0; margin:0.4em 0 0.2em;}
.wizardStep {padding:1em 1em 1em 1em;}
.wizard .button {margin:0.5em 0 0; font-size:1.2em;}
.wizardFooter {padding:0.8em 0.4em 0.8em 0;}
.wizardFooter .status {padding:0 0.4em; margin-left:1em;}
.wizard .button {padding:0.1em 0.2em;}

#messageArea {position:fixed; top:2em; right:0; margin:0.5em; padding:0.5em; z-index:2000; _position:absolute;}
.messageToolbar {display:block; text-align:right; padding:0.2em;}
#messageArea a {text-decoration:underline;}

.tiddlerPopupButton {padding:0.2em;}
.popupTiddler {position: absolute; z-index:300; padding:1em; margin:0;}

.popup {position:absolute; z-index:300; font-size:.9em; padding:0; list-style:none; margin:0;}
.popup .popupMessage {padding:0.4em;}
.popup hr {display:block; height:1px; width:auto; padding:0; margin:0.2em 0;}
.popup li.disabled {padding:0.4em;}
.popup li a {display:block; padding:0.4em; font-weight:normal; cursor:pointer;}
.listBreak {font-size:1px; line-height:1px;}
.listBreak div {margin:2px 0;}

.tabset {padding:1em 0 0 0.5em;}
.tab {margin:0 0 0 0.25em; padding:2px;}
.tabContents {padding:0.5em;}
.tabContents ul, .tabContents ol {margin:0; padding:0;}
.txtMainTab .tabContents li {list-style:none;}
.tabContents li.listLink { margin-left:.75em;}

#contentWrapper {display:block;}
#splashScreen {display:none;}

#displayArea {margin:1em 17em 0 14em;}

.toolbar {text-align:right; font-size:.9em;}

.tiddler {padding:1em 1em 0;}

.missing .viewer,.missing .title {font-style:italic;}

.title {font-size:1.6em; font-weight:bold;}

.missing .subtitle {display:none;}
.subtitle {font-size:1.1em;}

.tiddler .button {padding:0.2em 0.4em;}

.tagging {margin:0.5em 0.5em 0.5em 0; float:left; display:none;}
.isTag .tagging {display:block;}
.tagged {margin:0.5em; float:right;}
.tagging, .tagged {font-size:0.9em; padding:0.25em;}
.tagging ul, .tagged ul {list-style:none; margin:0.25em; padding:0;}
.tagClear {clear:both;}

.footer {font-size:.9em;}
.footer li {display:inline;}

.annotation {padding:0.5em; margin:0.5em;}

* html .viewer pre {width:99%; padding:0 0 1em 0;}
.viewer {line-height:1.4em; padding-top:0.5em;}
.viewer .button {margin:0 0.25em; padding:0 0.25em;}
.viewer blockquote {line-height:1.5em; padding-left:0.8em;margin-left:2.5em;}
.viewer ul, .viewer ol {margin-left:0.5em; padding-left:1.5em;}

.viewer table, table.twtable {border-collapse:collapse; margin:0.8em 1.0em;}
.viewer th, .viewer td, .viewer tr,.viewer caption,.twtable th, .twtable td, .twtable tr,.twtable caption {padding:3px;}
table.listView {font-size:0.85em; margin:0.8em 1.0em;}
table.listView th, table.listView td, table.listView tr {padding:0 3px 0 3px;}

.viewer pre {padding:0.5em; margin-left:0.5em; font-size:1.2em; line-height:1.4em; overflow:auto;}
.viewer code {font-size:1.2em; line-height:1.4em;}

.editor {font-size:1.1em;}
.editor input, .editor textarea {display:block; width:100%; font:inherit;}
.editorFooter {padding:0.25em 0; font-size:.9em;}
.editorFooter .button {padding-top:0; padding-bottom:0;}

.fieldsetFix {border:0; padding:0; margin:1px 0px;}

.zoomer {font-size:1.1em; position:absolute; overflow:hidden;}
.zoomer div {padding:1em;}

* html #backstage {width:99%;}
* html #backstageArea {width:99%;}
#backstageArea {display:none; position:relative; overflow: hidden; z-index:150; padding:0.3em 0.5em;}
#backstageToolbar {position:relative;}
#backstageArea a {font-weight:bold; margin-left:0.5em; padding:0.3em 0.5em;}
#backstageButton {display:none; position:absolute; z-index:175; top:0; right:0;}
#backstageButton a {padding:0.1em 0.4em; margin:0.1em;}
#backstage {position:relative; width:100%; z-index:50;}
#backstagePanel {display:none; z-index:100; position:absolute; width:90%; margin-left:3em; padding:1em;}
.backstagePanelFooter {padding-top:0.2em; float:right;}
.backstagePanelFooter a {padding:0.2em 0.4em;}
#backstageCloak {display:none; z-index:20; position:absolute; width:100%; height:100px;}

.whenBackstage {display:none;}
.backstageVisible .whenBackstage {display:block;}
/*}}}*/
/***
StyleSheet for ~SyntaxHighlighter
***/

/*{{{*/
.dp-highlighter
{
	font-family: "Consolas", "Courier New", Courier, mono, serif;
	font-size: 12px;
	background-color: #E7E5DC;
	width: 99%;
	overflow: auto;
	margin: 18px 0 18px 0 !important;
	padding-top: 1px; /* adds a little border on top when controls are hidden */
}

/* clear styles */
.dp-highlighter ol,
.dp-highlighter ol li,
.dp-highlighter ol li span 
{
	margin: 0;
	padding: 0;
	border: none;
}

.dp-highlighter a,
.dp-highlighter a:hover
{
	background: none;
	border: none;
	padding: 0;
	margin: 0;
}

.dp-highlighter .bar
{
	padding-left: 45px;
}

.dp-highlighter.collapsed .bar,
.dp-highlighter.nogutter .bar
{
	padding-left: 0px;
}

.dp-highlighter ol
{
	list-style: decimal; /* for ie */
	background-color: #fff;
	margin: 0px 0px 1px 45px !important; /* 1px bottom margin seems to fix occasional Firefox scrolling */
	padding: 0px;
	color: #5C5C5C;
}

.dp-highlighter.nogutter ol,
.dp-highlighter.nogutter ol li
{
	list-style: none !important;
	margin-left: 0px !important;
}

.dp-highlighter ol li,
.dp-highlighter .columns div
{
	list-style: decimal-leading-zero; /* better look for others, override cascade from OL */
	list-style-position: outside !important;
	border-left: 3px solid #6CE26C;
	background-color: #F8F8F8;
	color: #5C5C5C;
	padding: 0 3px 0 10px !important;
	margin: 0 !important;
	line-height: 14px;
}

.dp-highlighter.nogutter ol li,
.dp-highlighter.nogutter .columns div
{
	border: 0;
}

.dp-highlighter .columns
{
	background-color: #F8F8F8;
	color: gray;
	overflow: hidden;
	width: 100%;
}

.dp-highlighter .columns div
{
	padding-bottom: 5px;
}

.dp-highlighter ol li.alt
{
	background-color: #FFF;
	color: inherit;
}

.dp-highlighter ol li span
{
	color: black;
	background-color: inherit;
}

/* Adjust some properties when collapsed */

.dp-highlighter.collapsed ol
{
	margin: 0px;
}

.dp-highlighter.collapsed ol li
{
	display: none;
}

/* Additional modifications when in print-view */

.dp-highlighter.printing
{
	border: none;
}

.dp-highlighter.printing .tools
{
	display: none !important;
}

.dp-highlighter.printing li
{
	display: list-item !important;
}

/* Styles for the tools */

.dp-highlighter .tools
{
	padding: 3px 8px 3px 10px;
	font: 9px Verdana, Geneva, Arial, Helvetica, sans-serif;
	color: silver;
	background-color: #f8f8f8;
	padding-bottom: 10px;
	border-left: 3px solid #6CE26C;
}

.dp-highlighter.nogutter .tools
{
	border-left: 0;
}

.dp-highlighter.collapsed .tools
{
	border-bottom: 0;
}

.dp-highlighter .tools a
{
	font-size: 9px;
	color: #a0a0a0;
	background-color: inherit;
	text-decoration: none;
	margin-right: 10px;
}

.dp-highlighter .tools a:hover
{
	color: red;
	background-color: inherit;
	text-decoration: underline;
}

/* About dialog styles */

.dp-about { background-color: #fff; color: #333; margin: 0px; padding: 0px; }
.dp-about table { width: 100%; height: 100%; font-size: 11px; font-family: Tahoma, Verdana, Arial, sans-serif !important; }
.dp-about td { padding: 10px; vertical-align: top; }
.dp-about .copy { border-bottom: 1px solid #ACA899; height: 95%; }
.dp-about .title { color: red; background-color: inherit; font-weight: bold; }
.dp-about .para { margin: 0 0 4px 0; }
.dp-about .footer { background-color: #ECEADB; color: #333; border-top: 1px solid #fff; text-align: right; }
.dp-about .close { font-size: 11px; font-family: Tahoma, Verdana, Arial, sans-serif !important; background-color: #ECEADB; color: #333; width: 60px; height: 22px; }

/* Language specific styles */

.dp-highlighter .comment, .dp-highlighter .comments { color: #008200; background-color: inherit; }
.dp-highlighter .string { color: blue; background-color: inherit; }
.dp-highlighter .keyword { color: #069; font-weight: bold; background-color: inherit; }
.dp-highlighter .preprocessor { color: gray; background-color: inherit; }

/*}}}*/
/***
!Metadata:
|''Name:''|SyntaxHighlighterPlugin|
|''Description:''|Code Syntax Highlighter Plugin for TiddlyWiki.|
|''Version:''|1.1.3|
|''Date:''|Oct 24, 2008|
|''Source:''|http://www.coolcode.cn/show-310-1.html|
|''Author:''|Ma Bingyao (andot (at) ujn (dot) edu (dot) cn)|
|''License:''|[[GNU Lesser General Public License|http://www.gnu.org/licenses/lgpl.txt]]|
|''~CoreVersion:''|2.4.1|
|''Browser:''|Firefox 1.5+; InternetExplorer 6.0; Safari; Opera; Chrome; etc.|

!Syntax:
{{{
<code options>
codes
</code>
}}}

!Examples:
{{{
<code java>
public class HelloWorld {
    public static void main(String args[]) {
        System.out.println("HelloWorld!");
    }
}
</code>
}}}

!Revision History:
|''Version''|''Date''|''Note''|
|1.1.2|Oct 15, 2008|Optimize Highlight|
|1.0.0|Oct 13, 2008|Initial release|

!Code section:
***/
//{{{
var dp={sh:{Toolbar:{},Utils:{},RegexLib:{},Brushes:{},Strings:{AboutDialog:"<html><head><title>About...</title></head><body class=\"dp-about\"><table cellspacing=\"0\"><tr><td class=\"copy\"><p class=\"title\">dp.SyntaxHighlighter</div><div class=\"para\">Version: {V}</p><p><a href=\"http://www.dreamprojections.com/syntaxhighlighter/?ref=about\" target=\"_blank\">http://www.dreamprojections.com/syntaxhighlighter</a></p>&copy;2004-2007 Alex Gorbatchev.</td></tr><tr><td class=\"footer\"><input type=\"button\" class=\"close\" value=\"OK\" onClick=\"window.close()\"/></td></tr></table></body></html>"},ClipboardSwf:null,Version:"1.5.1"}};dp.SyntaxHighlighter=dp.sh;dp.sh.Toolbar.Commands={ExpandSource:{label:"+ expand source",check:function($){return $.collapse},func:function($,_){$.parentNode.removeChild($);_.div.className=_.div.className.replace("collapsed","")}},ViewSource:{label:"view plain",func:function($,_){var A=dp.sh.Utils.FixForBlogger(_.originalCode).replace(/</g,"&lt;"),B=window.open("","_blank","width=750, height=400, location=0, resizable=1, menubar=0, scrollbars=0");B.document.write("<textarea style=\"width:99%;height:99%\">"+A+"</textarea>");B.document.close()}},CopyToClipboard:{label:"copy to clipboard",check:function(){return window.clipboardData!=null||dp.sh.ClipboardSwf!=null},func:function($,A){var B=dp.sh.Utils.FixForBlogger(A.originalCode).replace(/&lt;/g,"<").replace(/&gt;/g,">").replace(/&amp;/g,"&");if(window.clipboardData)window.clipboardData.setData("text",B);else if(dp.sh.ClipboardSwf!=null){var _=A.flashCopier;if(_==null){_=document.createElement("div");A.flashCopier=_;A.div.appendChild(_)}_.innerHTML="<embed src=\""+dp.sh.ClipboardSwf+"\" FlashVars=\"clipboard="+encodeURIComponent(B)+"\" width=\"0\" height=\"0\" type=\"application/x-shockwave-flash\"></embed>"}alert("The code is in your clipboard now")}},PrintSource:{label:"print",func:function($,B){var _=document.createElement("IFRAME"),A=null;_.style.cssText="position:absolute;width:0px;height:0px;left:-500px;top:-500px;";document.body.appendChild(_);A=_.contentWindow.document;dp.sh.Utils.CopyStyles(A,window.document);A.write("<div class=\""+B.div.className.replace("collapsed","")+" printing\">"+B.div.innerHTML+"</div>");A.close();_.contentWindow.focus();_.contentWindow.print();alert("Printing...");document.body.removeChild(_)}},About:{label:"?",func:function(_){var A=window.open("","_blank","dialog,width=300,height=150,scrollbars=0"),$=A.document;dp.sh.Utils.CopyStyles($,window.document);$.write(dp.sh.Strings.AboutDialog.replace("{V}",dp.sh.Version));$.close();A.focus()}}};dp.sh.Toolbar.Create=function(B){var A=document.createElement("DIV");A.className="tools";for(var _ in dp.sh.Toolbar.Commands){var $=dp.sh.Toolbar.Commands[_];if($.check!=null&&!$.check(B))continue;A.innerHTML+="<a href=\"#\" onclick=\"dp.sh.Toolbar.Command('"+_+"',this);return false;\">"+$.label+"</a>"}return A};dp.sh.Toolbar.Command=function(_,$){var A=$;while(A!=null&&A.className.indexOf("dp-highlighter")==-1)A=A.parentNode;if(A!=null)dp.sh.Toolbar.Commands[_].func($,A.highlighter)};dp.sh.Utils.CopyStyles=function(A,_){var $=_.getElementsByTagName("link");for(var B=0;B<$.length;B++)if($[B].rel.toLowerCase()=="stylesheet")A.write("<link type=\"text/css\" rel=\"stylesheet\" href=\""+$[B].href+"\"></link>")};dp.sh.Utils.FixForBlogger=function($){return(dp.sh.isBloggerMode==true)?$.replace(/<br\s*\/?>|&lt;br\s*\/?&gt;/gi,"\n"):$};dp.sh.RegexLib={MultiLineCComments:new RegExp("/\\*[\\s\\S]*?\\*/","gm"),SingleLineCComments:new RegExp("//.*$","gm"),SingleLinePerlComments:new RegExp("#.*$","gm"),DoubleQuotedString:new RegExp("\"(?:\\.|(\\\\\\\")|[^\\\"\"\\n])*\"","g"),SingleQuotedString:new RegExp("'(?:\\.|(\\\\\\')|[^\\''\\n])*'","g")};dp.sh.Match=function(_,$,A){this.value=_;this.index=$;this.length=_.length;this.css=A};dp.sh.Highlighter=function(){this.noGutter=false;this.addControls=true;this.collapse=false;this.tabsToSpaces=true;this.wrapColumn=80;this.showColumns=true};dp.sh.Highlighter.SortCallback=function($,_){if($.index<_.index)return-1;else if($.index>_.index)return 1;else if($.length<_.length)return-1;else if($.length>_.length)return 1;return 0};dp.sh.Highlighter.prototype.CreateElement=function(_){var $=document.createElement(_);$.highlighter=this;return $};dp.sh.Highlighter.prototype.GetMatches=function(_,B){var $=0,A=null;while((A=_.exec(this.code))!=null)this.matches[this.matches.length]=new dp.sh.Match(A[0],A.index,B)};dp.sh.Highlighter.prototype.AddBit=function($,A){if($==null||$.length==0)return;var C=this.CreateElement("SPAN");$=$.replace(/ /g,"&nbsp;");$=$.replace(/</g,"&lt;");$=$.replace(/\n/gm,"&nbsp;<br>");if(A!=null){if((/br/gi).test($)){var _=$.split("&nbsp;<br>");for(var B=0;B<_.length;B++){C=this.CreateElement("SPAN");C.className=A;C.innerHTML=_[B];this.div.appendChild(C);if(B+1<_.length)this.div.appendChild(this.CreateElement("BR"))}}else{C.className=A;C.innerHTML=$;this.div.appendChild(C)}}else{C.innerHTML=$;this.div.appendChild(C)}};dp.sh.Highlighter.prototype.IsInside=function(_){if(_==null||_.length==0)return false;for(var A=0;A<this.matches.length;A++){var $=this.matches[A];if($==null)continue;if((_.index>$.index)&&(_.index<$.index+$.length))return true}return false};dp.sh.Highlighter.prototype.ProcessRegexList=function(){for(var $=0;$<this.regexList.length;$++)this.GetMatches(this.regexList[$].regex,this.regexList[$].css)};dp.sh.Highlighter.prototype.ProcessSmartTabs=function(E){var B=E.split("\n"),$="",D=4,A="\t";function _(A,E,_){var B=A.substr(0,E),C=A.substr(E+1,A.length),$="";for(var D=0;D<_;D++)$+=" ";return B+$+C}function C(B,C){if(B.indexOf(A)==-1)return B;var D=0;while((D=B.indexOf(A))!=-1){var $=C-D%C;B=_(B,D,$)}return B}for(var F=0;F<B.length;F++)$+=C(B[F],D)+"\n";return $};dp.sh.Highlighter.prototype.SwitchToList=function(){var C=this.div.innerHTML.replace(/<(br)\/?>/gi,"\n"),B=C.split("\n");if(this.addControls==true)this.bar.appendChild(dp.sh.Toolbar.Create(this));if(this.showColumns){var A=this.CreateElement("div"),_=this.CreateElement("div"),E=10,G=1;while(G<=150)if(G%E==0){A.innerHTML+=G;G+=(G+"").length}else{A.innerHTML+="&middot;";G++}_.className="columns";_.appendChild(A);this.bar.appendChild(_)}for(var G=0,D=this.firstLine;G<B.length-1;G++,D++){var $=this.CreateElement("LI"),F=this.CreateElement("SPAN");$.className=(G%2==0)?"alt":"";F.innerHTML=B[G]+"&nbsp;";$.appendChild(F);this.ol.appendChild($)}this.div.innerHTML=""};dp.sh.Highlighter.prototype.Highlight=function(C){function A($){return $.replace(/^\s*(.*?)[\s\n]*$/g,"$1")}function $($){return $.replace(/\n*$/,"").replace(/^\n*/,"")}function _(B){var E=dp.sh.Utils.FixForBlogger(B).split("\n"),C=new Array(),D=new RegExp("^\\s*","g"),$=1000;for(var F=0;F<E.length&&$>0;F++){if(A(E[F]).length==0)continue;var _=D.exec(E[F]);if(_!=null&&_.length>0)$=Math.min(_[0].length,$)}if($>0)for(F=0;F<E.length;F++)E[F]=E[F].substr($);return E.join("\n")}function D(A,$,_){return A.substr($,_-$)}var F=0;if(C==null)C="";this.originalCode=C;this.code=$(_(C));this.div=this.CreateElement("DIV");this.bar=this.CreateElement("DIV");this.ol=this.CreateElement("OL");this.matches=new Array();this.div.className="dp-highlighter";this.div.highlighter=this;this.bar.className="bar";this.ol.start=this.firstLine;if(this.CssClass!=null)this.ol.className=this.CssClass;if(this.collapse)this.div.className+=" collapsed";if(this.noGutter)this.div.className+=" nogutter";if(this.tabsToSpaces==true)this.code=this.ProcessSmartTabs(this.code);this.ProcessRegexList();if(this.matches.length==0){this.AddBit(this.code,null);this.SwitchToList();this.div.appendChild(this.bar);this.div.appendChild(this.ol);return}this.matches=this.matches.sort(dp.sh.Highlighter.SortCallback);for(var E=0;E<this.matches.length;E++)if(this.IsInside(this.matches[E]))this.matches[E]=null;for(E=0;E<this.matches.length;E++){var B=this.matches[E];if(B==null||B.length==0)continue;this.AddBit(D(this.code,F,B.index),null);this.AddBit(B.value,B.css);F=B.index+B.length}this.AddBit(this.code.substr(F),null);this.SwitchToList();this.div.appendChild(this.bar);this.div.appendChild(this.ol)};dp.sh.Highlighter.prototype.GetKeywords=function($){return"\\b"+$.replace(/ /g,"\\b|\\b")+"\\b"};dp.sh.BloggerMode=function(){dp.sh.isBloggerMode=true};dp.sh.HighlightAll=function(N,B,K,I,O,E){function A(){var $=arguments;for(var _=0;_<$.length;_++){if($[_]==null)continue;if(typeof($[_])=="string"&&$[_]!="")return $[_]+"";if(typeof($[_])=="object"&&$[_].value!="")return $[_].value+""}return null}function J($,_){for(var A=0;A<_.length;A++)if(_[A]==$)return true;return false}function L(A,B,C){var _=new RegExp("^"+A+"\\[(\\w+)\\]$","gi"),$=null;for(var D=0;D<B.length;D++)if(($=_.exec(B[D]))!=null)return $[1];return C}function C(B,A,_){var $=document.getElementsByTagName(_);for(var C=0;C<$.length;C++)if($[C].getAttribute("name")==A)B.push($[C])}var T=[],P=null,M={},$="innerHTML";C(T,N,"pre");C(T,N,"textarea");if(T.length==0)return;for(var R in dp.sh.Brushes){var F=dp.sh.Brushes[R].Aliases;if(F==null)continue;for(var G=0;G<F.length;G++)M[F[G]]=R}for(G=0;G<T.length;G++){var _=T[G],U=A(_.attributes["class"],_.className,_.attributes["language"],_.language),Q="";if(U==null)continue;U=U.split(":");Q=U[0].toLowerCase();if(M[Q]==null)continue;P=new dp.sh.Brushes[M[Q]]();_.style.display="none";P.noGutter=(B==null)?J("nogutter",U):!B;P.addControls=(K==null)?!J("nocontrols",U):K;P.collapse=(I==null)?J("collapse",U):I;P.showColumns=(E==null)?J("showcolumns",U):E;var D=document.getElementsByTagName("head")[0];if(P.Style&&D){var S=document.createElement("style");S.setAttribute("type","text/css");if(S.styleSheet)S.styleSheet.cssText=P.Style;else{var H=document.createTextNode(P.Style);S.appendChild(H)}D.appendChild(S)}P.firstLine=(O==null)?parseInt(L("firstline",U,1)):O;P.Highlight(_[$]);P.source=_;_.parentNode.insertBefore(P.div,_)}};version.extensions.SyntaxHighLighterPlugin={major:1,minor:1,revision:3,date:new Date(2008,10,24)};dp.sh.ClipboardSwf="clipboard.swf";dp.sh.Highlight=function(_,Q,B,J,H,M,D){function A(){var $=arguments;for(var _=0;_<$.length;_++){if($[_]==null)continue;if(typeof($[_])=="string"&&$[_]!="")return $[_]+"";if(typeof($[_])=="object"&&$[_].value!="")return $[_].value+""}return null}function I($,_){for(var A=0;A<_.length;A++)if(_[A]==$)return true;return false}function K(A,B,C){var _=new RegExp("^"+A+"\\[(\\w+)\\]$","gi"),$=null;for(var D=0;D<B.length;D++)if(($=_.exec(B[D]))!=null)return $[1];return C}var N=null,$="innerHTML";if(this.registered==undefined){var L={};for(var O in dp.sh.Brushes){var E=dp.sh.Brushes[O].Aliases;if(E==null)continue;for(var F=0;F<E.length;F++)L[E[F]]=O}this.registered=L}Q=Q.split(":");language=Q[0].toLowerCase();if(this.registered[language]==null)return;N=new dp.sh.Brushes[this.registered[language]]();_.style.display="none";N.noGutter=(B==null)?I("nogutter",Q):!B;N.addControls=(J==null)?!I("nocontrols",Q):J;N.collapse=(H==null)?I("collapse",Q):H;N.showColumns=(D==null)?I("showcolumns",Q):D;var C=document.getElementsByTagName("head")[0],P=document.getElementById(N.CssClass);if(N.Style&&C&&!P){P=document.createElement("style");P.setAttribute("id",N.CssClass);P.setAttribute("type","text/css");if(P.styleSheet)P.styleSheet.cssText=N.Style;else{var G=document.createTextNode(N.Style);P.appendChild(G)}C.appendChild(P)}N.firstLine=(M==null)?parseInt(K("firstline",Q,1)):M;N.Highlight(_[$]);N.source=_;_.parentNode.insertBefore(N.div,_)};config.formatters.push({name:"SyntaxHighlighter",match:"^<code[\\s]+[^>]+>\\n",element:"pre",handler:function(_){this.lookaheadRegExp=/<code[\s]+([^>]+)>\n((?:^[^\n]*\n)+?)(^<\/code>$\n?)/mg;this.lookaheadRegExp.lastIndex=_.matchStart;var $=this.lookaheadRegExp.exec(_.source);if($&&$.index==_.matchStart){var C=$[1],B=$[2];if(config.browser.isIE)B=B.replace(/\n/g,"\r");var A=createTiddlyElement(_.output,this.element,null,null,B);dp.sh.Highlight(A,C);_.nextMatch=$.index+$[0].length}}});config.formatterHelpers.enclosedTextHelper=function(_){this.lookaheadRegExp.lastIndex=_.matchStart;var $=this.lookaheadRegExp.exec(_.source);if($&&$.index==_.matchStart){var B=$[1];if(config.browser.isIE)B=B.replace(/\n/g,"\r");var A=createTiddlyElement(_.output,this.element,null,null,B);switch(_.matchText){case"/*{{{*/\n":dp.sh.Highlight(A,"css");break;case"//{{{\n":dp.sh.Highlight(A,"js");break;case"<!--{{{-->\n":dp.sh.Highlight(A,"xml");break}_.nextMatch=$.index+$[0].length}};dp.sh.Brushes.AS3=function(){var _="class interface package",$="Array Boolean Date decodeURI decodeURIComponent encodeURI encodeURIComponent escape "+"int isFinite isNaN isXMLName Number Object parseFloat parseInt "+"String trace uint unescape XML XMLList "+"Infinity -Infinity NaN undefined "+"as delete instanceof is new typeof "+"break case catch continue default do each else finally for if in "+"label return super switch throw try while with "+"dynamic final internal native override private protected public static "+"...rest const extends function get implements namespace set "+"import include use "+"AS3 flash_proxy object_proxy "+"false null this true "+"void Null";this.regexList=[{regex:dp.sh.RegexLib.SingleLineCComments,css:"comment"},{regex:dp.sh.RegexLib.MultiLineCComments,css:"blockcomment"},{regex:dp.sh.RegexLib.DoubleQuotedString,css:"string"},{regex:dp.sh.RegexLib.SingleQuotedString,css:"string"},{regex:new RegExp("^\\s*#.*","gm"),css:"preprocessor"},{regex:new RegExp(this.GetKeywords(_),"gm"),css:"definition"},{regex:new RegExp(this.GetKeywords($),"gm"),css:"keyword"},{regex:new RegExp("var","gm"),css:"variable"}];this.CssClass="dp-as";this.Style=".dp-as .comment { color: #009900; font-style: italic; }"+".dp-as .blockcomment { color: #3f5fbf; }"+".dp-as .string { color: #990000; }"+".dp-as .preprocessor { color: #0033ff; }"+".dp-as .definition { color: #9900cc; font-weight: bold; }"+".dp-as .keyword { color: #0033ff; }"+".dp-as .variable { color: #6699cc; font-weight: bold; }"};dp.sh.Brushes.AS3.prototype=new dp.sh.Highlighter();dp.sh.Brushes.AS3.Aliases=["as","actionscript","ActionScript","as3","AS3"];dp.sh.Brushes.Bash=function(){var _="alias bg bind break builtin cd command compgen complete continue "+"declare dirs disown echo enable eval exec exit export fc fg "+"getopts hash help history jobs kill let local logout popd printf "+"pushd pwd read readonly return set shift shopt source "+"suspend test times trap type typeset ulimit umask unalias unset wait",$="case do done elif else esac fi for function if in select then "+"time until while";this.regexList=[{regex:dp.sh.RegexLib.SingleLinePerlComments,css:"comment"},{regex:dp.sh.RegexLib.DoubleQuotedString,css:"string"},{regex:dp.sh.RegexLib.SingleQuotedString,css:"string"},{regex:new RegExp("[()[\\]{}]","g"),css:"delim"},{regex:new RegExp("\\$\\w+","g"),css:"vars"},{regex:new RegExp("\\w+=","g"),css:"vars"},{regex:new RegExp("\\s-\\w+","g"),css:"flag"},{regex:new RegExp(this.GetKeywords(_),"gm"),css:"builtin"},{regex:new RegExp(this.GetKeywords($),"gm"),css:"keyword"}];this.CssClass="dp-bash";this.Style=".dp-bash .builtin {color: maroon; font-weight: bold;}"+".dp-bash .comment {color: gray;}"+".dp-bash .delim {font-weight: bold;}"+".dp-bash .flag {color: green;}"+".dp-bash .string {color: red;}"+".dp-bash .vars {color: blue;}"};dp.sh.Brushes.Bash.prototype=new dp.sh.Highlighter();dp.sh.Brushes.Bash.Aliases=["bash","sh"];dp.sh.Brushes.Batch=function(){var _="APPEND ATTRIB CD CHDIR CHKDSK CHOICE CLS COPY DEL ERASE DELTREE "+"DIR EXIT FC COMP FDISK FIND FORMAT FSUTIL HELP JOIN "+"LABEL LOADFIX MK MKDIR MEM MEMMAKER MORE MOVE MSD PCPARK "+"PRINT RD RMDIR REN SCANDISK SHARE SORT SUBST SYS "+"TIME DATE TREE TRUENAME TYPE UNDELETE VER XCOPY",$="DO ELSE FOR IN CALL CHOICE GOTO SHIFT PAUSE ERRORLEVEL "+"IF NOT EXIST LFNFOR START SETLOCAL ENDLOCAL ECHO SET";this.regexList=[{regex:new RegExp("REM.*$","gm"),css:"comment"},{regex:new RegExp("::.*$","gm"),css:"comment"},{regex:dp.sh.RegexLib.DoubleQuotedString,css:"string"},{regex:dp.sh.RegexLib.SingleQuotedString,css:"string"},{regex:new RegExp("[()[\\]{}]","g"),css:"delim"},{regex:new RegExp("%\\w+%","g"),css:"vars"},{regex:new RegExp("%%\\w+","g"),css:"vars"},{regex:new RegExp("\\w+=","g"),css:"vars"},{regex:new RegExp("@\\w+","g"),css:"keyword"},{regex:new RegExp(":\\w+","g"),css:"keyword"},{regex:new RegExp("\\s/\\w+","g"),css:"flag"},{regex:new RegExp(this.GetKeywords(_),"gm"),css:"builtin"},{regex:new RegExp(this.GetKeywords($),"gm"),css:"keyword"}];this.CssClass="dp-batch";this.Style=".dp-batch .builtin {color: maroon; font-weight: bold;}"+".dp-batch .comment {color: gray;}"+".dp-batch .delim {font-weight: bold;}"+".dp-batch .flag {color: green;}"+".dp-batch .string {color: red;}"+".dp-batch .vars {color: blue;font-weight: bold;}"};dp.sh.Brushes.Batch.prototype=new dp.sh.Highlighter();dp.sh.Brushes.Batch.Aliases=["batch","dos"];dp.sh.Brushes.ColdFusion=function(){this.CssClass="dp-coldfusion";this.Style=".dp-coldfusion { font: 13px \"Courier New\", Courier, monospace; }"+".dp-coldfusion .tag, .dp-coldfusion .tag-name { color: #990033; }"+".dp-coldfusion .attribute { color: #990033; }"+".dp-coldfusion .attribute-value { color: #0000FF; }"+".dp-coldfusion .cfcomments { background-color: #FFFF99; color: #000000; }"+".dp-coldfusion .cfscriptcomments { color: #999999; }"+".dp-coldfusion .keywords { color: #0000FF; }"+".dp-coldfusion .mgkeywords { color: #CC9900; }"+".dp-coldfusion .numbers { color: #ff0000; }"+".dp-coldfusion .strings { color: green; }";this.mgKeywords="setvalue getvalue addresult viewcollection viewstate";this.keywords="var eq neq gt gte lt lte not and or true false "+"abs acos addsoaprequestheader addsoapresponseheader "+"arrayappend arrayavg arrayclear arraydeleteat arrayinsertat "+"arrayisempty arraylen arraymax arraymin arraynew "+"arrayprepend arrayresize arrayset arraysort arraysum "+"arrayswap arraytolist asc asin atn binarydecode binaryencode "+"bitand bitmaskclear bitmaskread bitmaskset bitnot bitor bitshln "+"bitshrn bitxor ceiling charsetdecode charsetencode chr cjustify "+"compare comparenocase cos createdate createdatetime createobject "+"createobject createobject createobject createobject createodbcdate "+"createodbcdatetime createodbctime createtime createtimespan "+"createuuid dateadd datecompare dateconvert datediff dateformat "+"datepart day dayofweek dayofweekasstring dayofyear daysinmonth "+"daysinyear de decimalformat decrementvalue decrypt decryptbinary "+"deleteclientvariable directoryexists dollarformat duplicate encrypt "+"encryptbinary evaluate exp expandpath fileexists find findnocase "+"findoneof firstdayofmonth fix formatbasen generatesecretkey "+"getauthuser getbasetagdata getbasetaglist getbasetemplatepath "+"getclientvariableslist getcontextroot getcurrenttemplatepath "+"getdirectoryfrompath getencoding getexception getfilefrompath "+"getfunctionlist getgatewayhelper gethttprequestdata gethttptimestring "+"getk2serverdoccount getk2serverdoccountlimit getlocale "+"getlocaledisplayname getlocalhostip getmetadata getmetricdata "+"getpagecontext getprofilesections getprofilestring getsoaprequest "+"getsoaprequestheader getsoapresponse getsoapresponseheader "+"gettempdirectory gettempfile gettemplatepath gettickcount "+"gettimezoneinfo gettoken hash hour htmlcodeformat htmleditformat "+"iif incrementvalue inputbasen insert int isarray isbinary isboolean "+"iscustomfunction isdate isdebugmode isdefined isk2serverabroker "+"isk2serverdoccountexceeded isk2serveronline isleapyear islocalhost "+"isnumeric isnumericdate isobject isquery issimplevalue issoaprequest "+"isstruct isuserinrole isvalid isvalid isvalid iswddx isxml "+"isxmlattribute isxmldoc isxmlelem isxmlnode isxmlroot javacast "+"jsstringformat lcase left len listappend listchangedelims listcontains "+"listcontainsnocase listdeleteat listfind listfindnocase listfirst "+"listgetat listinsertat listlast listlen listprepend listqualify "+"listrest listsetat listsort listtoarray listvaluecount "+"listvaluecountnocase ljustify log log10 lscurrencyformat lsdateformat "+"lseurocurrencyformat lsiscurrency lsisdate lsisnumeric lsnumberformat "+"lsparsecurrency lsparsedatetime lsparseeurocurrency lsparsenumber "+"lstimeformat ltrim max mid min minute month monthasstring now "+"numberformat paragraphformat parameterexists parsedatetime pi "+"preservesinglequotes quarter queryaddcolumn queryaddrow querynew "+"querysetcell quotedvaluelist rand randomize randrange refind "+"refindnocase releasecomobject removechars repeatstring replace "+"replacelist replacenocase rereplace rereplacenocase reverse right "+"rjustify round rtrim second sendgatewaymessage setencoding "+"setlocale setprofilestring setvariable sgn sin spanexcluding "+"spanincluding sqr stripcr structappend structclear structcopy "+"structcount structdelete structfind structfindkey structfindvalue "+"structget structinsert structisempty structkeyarray structkeyexists "+"structkeylist structnew structsort structupdate tan timeformat "+"tobase64 tobinary toscript tostring trim ucase urldecode urlencodedformat "+"urlsessionformat val valuelist week wrap writeoutput xmlchildpos "+"xmlelemnew xmlformat xmlgetnodetype xmlnew xmlparse xmlsearch xmltransform "+"xmlvalidate year yesnoformat";this.stringMatches=new Array();this.attributeMatches=new Array()};dp.sh.Brushes.ColdFusion.prototype=new dp.sh.Highlighter();dp.sh.Brushes.ColdFusion.Aliases=["coldfusion","cf"];dp.sh.Brushes.ColdFusion.prototype.ProcessRegexList=function(){function B(_,$){_[_.length]=$}function A(A,$){for(var _=0;_<A.length;_++)if(A[_]==$)return _;return-1}var _=null,$=null;this.GetMatches(new RegExp("\\b(\\d+)","gm"),"numbers");this.GetMatches(new RegExp(this.GetKeywords(this.mgKeywords),"igm"),"mgkeywords");this.GetMatches(dp.sh.RegexLib.SingleLineCComments,"cfscriptcomments");this.GetMatches(dp.sh.RegexLib.MultiLineCComments,"cfscriptcomments");this.GetMatches(new RegExp("(&lt;|<)!---[\\s\\S]*?---(&gt;|>)","gm"),"cfcomments");$=new RegExp("(cfset\\s*)?([:\\w-.]+)\\s*=\\s*(\".*?\"|'.*?')*","gm");while((_=$.exec(this.code))!=null){if(_[1]!=undefined&&_[1]!="")continue;if(_[3]!=undefined&&_[3]!=""&&_[3]!="\"\""&&_[3]!="''"){B(this.matches,new dp.sh.Match(_[2],_.index,"attribute"));B(this.matches,new dp.sh.Match(_[3],_.index+_[0].indexOf(_[3]),"attribute-value"));B(this.stringMatches,_[3]);B(this.attributeMatches,_[2])}}this.GetMatches(new RegExp("(&lt;|<)/*\\?*(?!\\!)|/*\\?*(&gt;|>)","gm"),"tag");$=new RegExp("(?:&lt;|<)/*\\?*\\s*([:\\w-.]+)","gm");while((_=$.exec(this.code))!=null)B(this.matches,new dp.sh.Match(_[1],_.index+_[0].indexOf(_[1]),"tag-name"));$=new RegExp(this.GetKeywords(this.keywords),"igm");while((_=$.exec(this.code))!=null)if(A(this.attributeMatches,_[0])==-1)B(this.matches,new dp.sh.Match(_[0],_.index,"keywords"));$=new RegExp("cfset\\s*.*(\".*?\"|'.*?')","gm");while((_=$.exec(this.code))!=null)if(_[1]!=undefined&&_[1]!=""){B(this.matches,new dp.sh.Match(_[1],_.index+_[0].indexOf(_[1]),"strings"));B(this.stringMatches,_[1])}while((_=dp.sh.RegexLib.DoubleQuotedString.exec(this.code))!=null)if(A(this.stringMatches,_[0])==-1)B(this.matches,new dp.sh.Match(_[0],_.index,"strings"));while((_=dp.sh.RegexLib.SingleQuotedString.exec(this.code))!=null)if(A(this.stringMatches,_[0])==-1)B(this.matches,new dp.sh.Match(_[0],_.index,"strings"))};dp.sh.Brushes.Cpp=function(){var _="ATOM BOOL BOOLEAN BYTE CHAR COLORREF DWORD DWORDLONG DWORD_PTR "+"DWORD32 DWORD64 FLOAT HACCEL HALF_PTR HANDLE HBITMAP HBRUSH "+"HCOLORSPACE HCONV HCONVLIST HCURSOR HDC HDDEDATA HDESK HDROP HDWP "+"HENHMETAFILE HFILE HFONT HGDIOBJ HGLOBAL HHOOK HICON HINSTANCE HKEY "+"HKL HLOCAL HMENU HMETAFILE HMODULE HMONITOR HPALETTE HPEN HRESULT "+"HRGN HRSRC HSZ HWINSTA HWND INT INT_PTR INT32 INT64 LANGID LCID LCTYPE "+"LGRPID LONG LONGLONG LONG_PTR LONG32 LONG64 LPARAM LPBOOL LPBYTE LPCOLORREF "+"LPCSTR LPCTSTR LPCVOID LPCWSTR LPDWORD LPHANDLE LPINT LPLONG LPSTR LPTSTR "+"LPVOID LPWORD LPWSTR LRESULT PBOOL PBOOLEAN PBYTE PCHAR PCSTR PCTSTR PCWSTR "+"PDWORDLONG PDWORD_PTR PDWORD32 PDWORD64 PFLOAT PHALF_PTR PHANDLE PHKEY PINT "+"PINT_PTR PINT32 PINT64 PLCID PLONG PLONGLONG PLONG_PTR PLONG32 PLONG64 POINTER_32 "+"POINTER_64 PSHORT PSIZE_T PSSIZE_T PSTR PTBYTE PTCHAR PTSTR PUCHAR PUHALF_PTR "+"PUINT PUINT_PTR PUINT32 PUINT64 PULONG PULONGLONG PULONG_PTR PULONG32 PULONG64 "+"PUSHORT PVOID PWCHAR PWORD PWSTR SC_HANDLE SC_LOCK SERVICE_STATUS_HANDLE SHORT "+"SIZE_T SSIZE_T TBYTE TCHAR UCHAR UHALF_PTR UINT UINT_PTR UINT32 UINT64 ULONG "+"ULONGLONG ULONG_PTR ULONG32 ULONG64 USHORT USN VOID WCHAR WORD WPARAM WPARAM WPARAM "+"char bool short int __int32 __int64 __int8 __int16 long float double __wchar_t "+"clock_t _complex _dev_t _diskfree_t div_t ldiv_t _exception _EXCEPTION_POINTERS "+"FILE _finddata_t _finddatai64_t _wfinddata_t _wfinddatai64_t __finddata64_t "+"__wfinddata64_t _FPIEEE_RECORD fpos_t _HEAPINFO _HFILE lconv intptr_t "+"jmp_buf mbstate_t _off_t _onexit_t _PNH ptrdiff_t _purecall_handler "+"sig_atomic_t size_t _stat __stat64 _stati64 terminate_function "+"time_t __time64_t _timeb __timeb64 tm uintptr_t _utimbuf "+"va_list wchar_t wctrans_t wctype_t wint_t signed",$="break case catch class const __finally __exception __try "+"const_cast continue private public protected __declspec "+"default delete deprecated dllexport dllimport do dynamic_cast "+"else enum explicit extern if for friend goto inline "+"mutable naked namespace new noinline noreturn nothrow "+"register reinterpret_cast return selectany "+"sizeof static static_cast struct switch template this "+"thread throw true false try typedef typeid typename union "+"using uuid virtual void volatile whcar_t while";this.regexList=[{regex:dp.sh.RegexLib.SingleLineCComments,css:"comment"},{regex:dp.sh.RegexLib.MultiLineCComments,css:"comment"},{regex:dp.sh.RegexLib.DoubleQuotedString,css:"string"},{regex:dp.sh.RegexLib.SingleQuotedString,css:"string"},{regex:new RegExp("^ *#.*","gm"),css:"preprocessor"},{regex:new RegExp(this.GetKeywords(_),"gm"),css:"datatypes"},{regex:new RegExp(this.GetKeywords($),"gm"),css:"keyword"}];this.CssClass="dp-cpp";this.Style=".dp-cpp .datatypes { color: #2E8B57; font-weight: bold; }"};dp.sh.Brushes.Cpp.prototype=new dp.sh.Highlighter();dp.sh.Brushes.Cpp.Aliases=["cpp","c","c++"];dp.sh.Brushes.CSharp=function(){var $="abstract as base bool break byte case catch char checked class const "+"continue decimal default delegate do double else enum event explicit "+"extern false finally fixed float for foreach get goto if implicit in int "+"interface internal is lock long namespace new null object operator out "+"override params private protected public readonly ref return sbyte sealed set "+"short sizeof stackalloc static string struct switch this throw true try "+"typeof uint ulong unchecked unsafe ushort using virtual void while";this.regexList=[{regex:dp.sh.RegexLib.SingleLineCComments,css:"comment"},{regex:dp.sh.RegexLib.MultiLineCComments,css:"comment"},{regex:dp.sh.RegexLib.DoubleQuotedString,css:"string"},{regex:dp.sh.RegexLib.SingleQuotedString,css:"string"},{regex:new RegExp("^\\s*#.*","gm"),css:"preprocessor"},{regex:new RegExp(this.GetKeywords($),"gm"),css:"keyword"}];this.CssClass="dp-c";this.Style=".dp-c .vars { color: #d00; }"};dp.sh.Brushes.CSharp.prototype=new dp.sh.Highlighter();dp.sh.Brushes.CSharp.Aliases=["c#","c-sharp","csharp"];dp.sh.Brushes.CSS=function(){var _="ascent azimuth background-attachment background-color background-image background-position "+"background-repeat background baseline bbox border-collapse border-color border-spacing border-style border-top "+"border-right border-bottom border-left border-top-color border-right-color border-bottom-color border-left-color "+"border-top-style border-right-style border-bottom-style border-left-style border-top-width border-right-width "+"border-bottom-width border-left-width border-width border cap-height caption-side centerline clear clip color "+"content counter-increment counter-reset cue-after cue-before cue cursor definition-src descent direction display "+"elevation empty-cells float font-size-adjust font-family font-size font-stretch font-style font-variant font-weight font "+"height letter-spacing line-height list-style-image list-style-position list-style-type list-style margin-top "+"margin-right margin-bottom margin-left margin marker-offset marks mathline max-height max-width min-height min-width orphans "+"outline-color outline-style outline-width outline overflow padding-top padding-right padding-bottom padding-left padding page "+"page-break-after page-break-before page-break-inside pause pause-after pause-before pitch pitch-range play-during position "+"quotes richness size slope src speak-header speak-numeral speak-punctuation speak speech-rate stemh stemv stress "+"table-layout text-align text-decoration text-indent text-shadow text-transform unicode-bidi unicode-range units-per-em "+"vertical-align visibility voice-family volume white-space widows width widths word-spacing x-height z-index",$="above absolute all always aqua armenian attr aural auto avoid baseline behind below bidi-override black blink block blue bold bolder "+"both bottom braille capitalize caption center center-left center-right circle close-quote code collapse compact condensed "+"continuous counter counters crop cross crosshair cursive dashed decimal decimal-leading-zero default digits disc dotted double "+"embed embossed e-resize expanded extra-condensed extra-expanded fantasy far-left far-right fast faster fixed format fuchsia "+"gray green groove handheld hebrew help hidden hide high higher icon inline-table inline inset inside invert italic "+"justify landscape large larger left-side left leftwards level lighter lime line-through list-item local loud lower-alpha "+"lowercase lower-greek lower-latin lower-roman lower low ltr marker maroon medium message-box middle mix move narrower "+"navy ne-resize no-close-quote none no-open-quote no-repeat normal nowrap n-resize nw-resize oblique olive once open-quote outset "+"outside overline pointer portrait pre print projection purple red relative repeat repeat-x repeat-y rgb ridge right right-side "+"rightwards rtl run-in screen scroll semi-condensed semi-expanded separate se-resize show silent silver slower slow "+"small small-caps small-caption smaller soft solid speech spell-out square s-resize static status-bar sub super sw-resize "+"table-caption table-cell table-column table-column-group table-footer-group table-header-group table-row table-row-group teal "+"text-bottom text-top thick thin top transparent tty tv ultra-condensed ultra-expanded underline upper-alpha uppercase upper-latin "+"upper-roman url visible wait white wider w-resize x-fast x-high x-large x-loud x-low x-slow x-small x-soft xx-large xx-small yellow",A="[mM]onospace [tT]ahoma [vV]erdana [aA]rial [hH]elvetica [sS]ans-serif [sS]erif";this.regexList=[{regex:dp.sh.RegexLib.MultiLineCComments,css:"comment"},{regex:dp.sh.RegexLib.DoubleQuotedString,css:"string"},{regex:dp.sh.RegexLib.SingleQuotedString,css:"string"},{regex:new RegExp("\\#[a-zA-Z0-9]{3,6}","g"),css:"value"},{regex:new RegExp("(-?\\d+)(.\\d+)?(px|em|pt|:|%|)","g"),css:"value"},{regex:new RegExp("!important","g"),css:"important"},{regex:new RegExp(this.GetKeywordsCSS(_),"gm"),css:"keyword"},{regex:new RegExp(this.GetValuesCSS($),"g"),css:"value"},{regex:new RegExp(this.GetValuesCSS(A),"g"),css:"value"}];this.CssClass="dp-css";this.Style=".dp-css .value { color: black; }"+".dp-css .important { color: red; }"};dp.sh.Highlighter.prototype.GetKeywordsCSS=function($){return"\\b([a-z_]|)"+$.replace(/ /g,"(?=:)\\b|\\b([a-z_\\*]|\\*|)")+"(?=:)\\b"};dp.sh.Highlighter.prototype.GetValuesCSS=function($){return"\\b"+$.replace(/ /g,"(?!-)(?!:)\\b|\\b()")+":\\b"};dp.sh.Brushes.CSS.prototype=new dp.sh.Highlighter();dp.sh.Brushes.CSS.Aliases=["css"];dp.sh.Brushes.Delphi=function(){var $="abs addr and ansichar ansistring array as asm begin boolean byte cardinal "+"case char class comp const constructor currency destructor div do double "+"downto else end except exports extended false file finalization finally "+"for function goto if implementation in inherited int64 initialization "+"integer interface is label library longint longword mod nil not object "+"of on or packed pansichar pansistring pchar pcurrency pdatetime pextended "+"pint64 pointer private procedure program property pshortstring pstring "+"pvariant pwidechar pwidestring protected public published raise real real48 "+"record repeat set shl shortint shortstring shr single smallint string then "+"threadvar to true try type unit until uses val var varirnt while widechar "+"widestring with word write writeln xor";this.regexList=[{regex:new RegExp("\\(\\*[\\s\\S]*?\\*\\)","gm"),css:"comment"},{regex:new RegExp("{(?!\\$)[\\s\\S]*?}","gm"),css:"comment"},{regex:dp.sh.RegexLib.SingleLineCComments,css:"comment"},{regex:dp.sh.RegexLib.SingleQuotedString,css:"string"},{regex:new RegExp("\\{\\$[a-zA-Z]+ .+\\}","g"),css:"directive"},{regex:new RegExp("\\b[\\d\\.]+\\b","g"),css:"number"},{regex:new RegExp("\\$[a-zA-Z0-9]+\\b","g"),css:"number"},{regex:new RegExp(this.GetKeywords($),"gm"),css:"keyword"}];this.CssClass="dp-delphi";this.Style=".dp-delphi .number { color: blue; }"+".dp-delphi .directive { color: #008284; }"+".dp-delphi .vars { color: #000; }"};dp.sh.Brushes.Delphi.prototype=new dp.sh.Highlighter();dp.sh.Brushes.Delphi.Aliases=["delphi","pascal"];dp.sh.Brushes.Java=function(){var $="abstract assert boolean break byte case catch char class const "+"continue default do double else enum extends "+"false final finally float for goto if implements import "+"instanceof int interface long native new null "+"package private protected public return "+"short static strictfp super switch synchronized this throw throws true "+"transient try void volatile while";this.regexList=[{regex:dp.sh.RegexLib.SingleLineCComments,css:"comment"},{regex:dp.sh.RegexLib.MultiLineCComments,css:"comment"},{regex:dp.sh.RegexLib.DoubleQuotedString,css:"string"},{regex:dp.sh.RegexLib.SingleQuotedString,css:"string"},{regex:new RegExp("\\b([\\d]+(\\.[\\d]+)?|0x[a-f0-9]+)\\b","gi"),css:"number"},{regex:new RegExp("(?!\\@interface\\b)\\@[\\$\\w]+\\b","g"),css:"annotation"},{regex:new RegExp("\\@interface\\b","g"),css:"keyword"},{regex:new RegExp(this.GetKeywords($),"gm"),css:"keyword"}];this.CssClass="dp-j";this.Style=".dp-j .annotation { color: #646464; }"+".dp-j .number { color: #C00000; }"};dp.sh.Brushes.Java.prototype=new dp.sh.Highlighter();dp.sh.Brushes.Java.Aliases=["java"];dp.sh.Brushes.JScript=function(){var $="abstract boolean break byte case catch char class const continue debugger "+"default delete do double else enum export extends false final finally float "+"for function goto if implements import in instanceof int interface long native "+"new null package private protected public return short static super switch "+"synchronized this throw throws transient true try typeof var void volatile while with";this.regexList=[{regex:dp.sh.RegexLib.SingleLineCComments,css:"comment"},{regex:dp.sh.RegexLib.MultiLineCComments,css:"comment"},{regex:dp.sh.RegexLib.DoubleQuotedString,css:"string"},{regex:dp.sh.RegexLib.SingleQuotedString,css:"string"},{regex:new RegExp("^\\s*#.*","gm"),css:"preprocessor"},{regex:new RegExp(this.GetKeywords($),"gm"),css:"keyword"}];this.CssClass="dp-c"};dp.sh.Brushes.JScript.prototype=new dp.sh.Highlighter();dp.sh.Brushes.JScript.Aliases=["js","jscript","javascript"];dp.sh.Brushes.Lua=function(){var $="break do end else elseif function if local nil not or repeat return and then until while this",_="math\\.\\w+ string\\.\\w+ os\\.\\w+ debug\\.\\w+ io\\.\\w+ error fopen dofile coroutine\\.\\w+ arg getmetatable ipairs loadfile loadlib loadstring longjmp print rawget rawset seek setmetatable assert tonumber tostring";this.regexList=[{regex:new RegExp("--\\[\\[[\\s\\S]*\\]\\]--","gm"),css:"comment"},{regex:new RegExp("--[^\\[]{2}.*$","gm"),css:"comment"},{regex:dp.sh.RegexLib.DoubleQuotedString,css:"string"},{regex:dp.sh.RegexLib.SingleQuotedString,css:"string"},{regex:new RegExp(this.GetKeywords($),"gm"),css:"keyword"},{regex:new RegExp(this.GetKeywords(_),"gm"),css:"func"},];this.CssClass="dp-lua"};dp.sh.Brushes.Lua.prototype=new dp.sh.Highlighter();dp.sh.Brushes.Lua.Aliases=["lua"];dp.sh.Brushes.Mxml=function(){this.CssClass="dp-mxml";this.Style=".dp-mxml .cdata { color: #000000; }"+".dp-mxml .tag { color : #0000ff; }"+".dp-mxml .tag-name { color: #0000ff; }"+".dp-mxml .script { color: green; }"+".dp-mxml .metadata { color: green; }"+".dp-mxml .attribute { color: #000000; }"+".dp-mxml .attribute-value { color: #990000; }"+".dp-mxml .trace { color: #cc6666; }"+".dp-mxml .var { color: #6699cc; }"+".dp-mxml .comment { color: #009900; }"+".dp-mxml .string { color: #990000; }"+".dp-mxml .keyword { color: blue; }"};dp.sh.Brushes.Mxml.prototype=new dp.sh.Highlighter();dp.sh.Brushes.Mxml.Aliases=["mxml"];dp.sh.Brushes.Mxml.prototype.ProcessRegexList=function(){function H(_,$){_[_.length]=$}function B(B,_){var A=0,$=false;for(A=0;A<B.length;A++)if(_.index>B[A].firstIndex&&_.index<B[A].lastIndex)$=true;return $}var $=0,F=null,D=null,A=null,C="",E=new Array(),_="abstract boolean break byte case catch char class const continue debugger "+"default delete do double else enum export extends false final finally float "+"for function goto if implements import in instanceof int interface long native "+"new null package private protected public return short static super switch "+"synchronized this throw throws transient true try typeof var void volatile while with",G=[{regex:dp.sh.RegexLib.SingleLineCComments,css:"comment"},{regex:dp.sh.RegexLib.MultiLineCComments,css:"comment"},{regex:dp.sh.RegexLib.DoubleQuotedString,css:"string"},{regex:dp.sh.RegexLib.SingleQuotedString,css:"string"},{regex:new RegExp("^\\s*#.*","gm"),css:"preprocessor"},{regex:new RegExp(this.GetKeywords("trace"),"gm"),css:"trace"},{regex:new RegExp(this.GetKeywords(_),"gm"),css:"keyword"}];A=new RegExp("&lt;\\!\\[CDATA\\[(.|\\s)*?\\]\\]&gt;","gm");while((F=A.exec(this.code))!=null){C=F[0].substr(0,12);H(this.matches,new dp.sh.Match(C,F.index,"cdata"));C=F[0].substr(12,F[0].length-12-6);for(var I=0;I<G.length;I++)while((D=G[I].regex.exec(C))!=null)H(this.matches,new dp.sh.Match(D[0],F.index+12+D.index,G[I].css));C=F[0].substr(F[0].length-6,6);H(this.matches,new dp.sh.Match(C,F.index+F[0].length-6,"cdata"));E.push({firstIndex:F.index,lastIndex:F.index+F[0].length-1})}this.GetMatches(new RegExp("(&lt;|<)!--\\s*.*?\\s*--(&gt;|>)","gm"),"comments");A=new RegExp("([:\\w-.]+)\\s*=\\s*(\".*?\"|'.*?'|\\w+)*|(\\w+)","gm");while((F=A.exec(this.code))!=null){if(F[1]==null)continue;if(B(E,F))continue;H(this.matches,new dp.sh.Match(F[1],F.index,"attribute"));if(F[2]!=undefined)H(this.matches,new dp.sh.Match(F[2],F.index+F[0].indexOf(F[2]),"attribute-value"))}A=new RegExp("(?:&lt;|<)/*\\?*\\s*([:\\w-.]+)","gm");while((F=A.exec(this.code))!=null){if(B(E,F))continue;C=F[0].substr(4,F[0].length-4);switch(C){case"mx:Script":case"/mx:Script":H(this.matches,new dp.sh.Match(F[0]+"&gt;",F.index,"script"));break;case"mx:Metadata":case"/mx:Metadata":H(this.matches,new dp.sh.Match(F[0]+"&gt;",F.index,"metadata"));break;default:H(this.matches,new dp.sh.Match(F[0],F.index,"tag-name"));break}}A=new RegExp("\\?&gt;|&gt;|/&gt;","gm");while((F=A.exec(this.code))!=null){if(B(E,F))continue;H(this.matches,new dp.sh.Match(F[0],F.index,"tag"))}};dp.sh.Brushes.Perl=function(){var _="abs accept alarm atan2 bind binmode bless caller chdir chmod chomp chop chown chr chroot close closedir connect cos crypt dbmclose dbmopen defined delete dump each endgrent endhostent endnetent endprotoent endpwent endservent eof exec exists exp fcntl fileno flock fork format formline getc getgrent getgrgid getgrnam gethostbyaddr gethostbyname gethostent getlogin getnetbyaddr getnetbyname getnetent getpeername getpgrp getppid getpriority getprotobyname getprotobynumber getprotoent getpwent getpwnam getpwuid getservbyname getservbyport getservent getsockname getsockopt glob gmtime grep hex import index int ioctl join keys kill lc lcfirst length link listen localtime lock log lstat m map mkdir msgctl msgget msgrcv msgsnd no oct open opendir ord pack pipe pop pos print printf prototype push q qq quotemeta qw qx rand read readdir readline readlink readpipe recv ref rename reset reverse rewinddir rindex rmdir scalar seek seekdir semctl semget semop send setgrent sethostent setnetent setpgrp setpriority setprotoent setpwent setservent setsockopt shift shmctl shmget shmread shmwrite shutdown sin sleep socket socketpair sort splice split sprintf sqrt srand stat study sub substr symlink syscall sysopen sysread sysseek system syswrite tell telldir tie tied time times tr truncate uc ucfirst umask undef unlink unpack unshift untie utime values vec waitpid wantarray warn write qr",$="s select goto die do package redo require return continue for foreach last next wait while use if else elsif eval exit unless switch case",A="my our local";this.regexList=[{regex:dp.sh.RegexLib.SingleLinePerlComments,css:"comment"},{regex:dp.sh.RegexLib.DoubleQuotedString,css:"string"},{regex:dp.sh.RegexLib.SingleQuotedString,css:"string"},{regex:new RegExp("(\\$|@|%)\\w+","g"),css:"vars"},{regex:new RegExp(this.GetKeywords(_),"gmi"),css:"func"},{regex:new RegExp(this.GetKeywords($),"gm"),css:"keyword"},{regex:new RegExp(this.GetKeywords(A),"gm"),css:"declarations"}];this.CssClass="dp-perl"};dp.sh.Brushes.Perl.prototype=new dp.sh.Highlighter();dp.sh.Brushes.Perl.Aliases=["perl"];dp.sh.Brushes.Php=function(){var _="abs acos acosh addcslashes addslashes "+"array_change_key_case array_chunk array_combine array_count_values array_diff "+"array_diff_assoc array_diff_key array_diff_uassoc array_diff_ukey array_fill "+"array_filter array_flip array_intersect array_intersect_assoc array_intersect_key "+"array_intersect_uassoc array_intersect_ukey array_key_exists array_keys array_map "+"array_merge array_merge_recursive array_multisort array_pad array_pop array_product "+"array_push array_rand array_reduce array_reverse array_search array_shift "+"array_slice array_splice array_sum array_udiff array_udiff_assoc "+"array_udiff_uassoc array_uintersect array_uintersect_assoc "+"array_uintersect_uassoc array_unique array_unshift array_values array_walk "+"array_walk_recursive atan atan2 atanh base64_decode base64_encode base_convert "+"basename bcadd bccomp bcdiv bcmod bcmul bindec bindtextdomain bzclose bzcompress "+"bzdecompress bzerrno bzerror bzerrstr bzflush bzopen bzread bzwrite ceil chdir "+"checkdate checkdnsrr chgrp chmod chop chown chr chroot chunk_split class_exists "+"closedir closelog copy cos cosh count count_chars date decbin dechex decoct "+"deg2rad delete ebcdic2ascii echo empty end ereg ereg_replace eregi eregi_replace error_log "+"error_reporting escapeshellarg escapeshellcmd eval exec exit exp explode extension_loaded "+"feof fflush fgetc fgetcsv fgets fgetss file_exists file_get_contents file_put_contents "+"fileatime filectime filegroup fileinode filemtime fileowner fileperms filesize filetype "+"floatval flock floor flush fmod fnmatch fopen fpassthru fprintf fputcsv fputs fread fscanf "+"fseek fsockopen fstat ftell ftok getallheaders getcwd getdate getenv gethostbyaddr gethostbyname "+"gethostbynamel getimagesize getlastmod getmxrr getmygid getmyinode getmypid getmyuid getopt "+"getprotobyname getprotobynumber getrandmax getrusage getservbyname getservbyport gettext "+"gettimeofday gettype glob gmdate gmmktime ini_alter ini_get ini_get_all ini_restore ini_set "+"interface_exists intval ip2long is_a is_array is_bool is_callable is_dir is_double "+"is_executable is_file is_finite is_float is_infinite is_int is_integer is_link is_long "+"is_nan is_null is_numeric is_object is_readable is_real is_resource is_scalar is_soap_fault "+"is_string is_subclass_of is_uploaded_file is_writable is_writeable mkdir mktime nl2br "+"parse_ini_file parse_str parse_url passthru pathinfo readlink realpath rewind rewinddir rmdir "+"round str_ireplace str_pad str_repeat str_replace str_rot13 str_shuffle str_split "+"str_word_count strcasecmp strchr strcmp strcoll strcspn strftime strip_tags stripcslashes "+"stripos stripslashes stristr strlen strnatcasecmp strnatcmp strncasecmp strncmp strpbrk "+"strpos strptime strrchr strrev strripos strrpos strspn strstr strtok strtolower strtotime "+"strtoupper strtr strval substr substr_compare",$="and or xor __FILE__ __LINE__ array as break case "+"cfunction class const continue declare default die do else "+"elseif empty enddeclare endfor endforeach endif endswitch endwhile "+"extends for foreach function include include_once global if "+"new old_function return static switch use require require_once "+"var while __FUNCTION__ __CLASS__ "+"__METHOD__ abstract interface public implements extends private protected throw";this.regexList=[{regex:dp.sh.RegexLib.SingleLineCComments,css:"comment"},{regex:dp.sh.RegexLib.MultiLineCComments,css:"comment"},{regex:dp.sh.RegexLib.DoubleQuotedString,css:"string"},{regex:dp.sh.RegexLib.SingleQuotedString,css:"string"},{regex:new RegExp("\\$\\w+","g"),css:"vars"},{regex:new RegExp(this.GetKeywords(_),"gmi"),css:"func"},{regex:new RegExp(this.GetKeywords($),"gm"),css:"keyword"}];this.CssClass="dp-c"};dp.sh.Brushes.Php.prototype=new dp.sh.Highlighter();dp.sh.Brushes.Php.Aliases=["php"];dp.sh.Brushes.Python=function(){var $="and assert break class continue def del elif else "+"except exec finally for from global if import in is "+"lambda not or pass print raise return try yield while",_="None True False self cls class_";this.regexList=[{regex:dp.sh.RegexLib.SingleLinePerlComments,css:"comment"},{regex:new RegExp("^\\s*@\\w+","gm"),css:"decorator"},{regex:new RegExp("(['\"]{3})([^\\1])*?\\1","gm"),css:"comment"},{regex:new RegExp("\"(?!\")(?:\\.|\\\\\\\"|[^\\\"\"\\n\\r])*\"","gm"),css:"string"},{regex:new RegExp("'(?!')*(?:\\.|(\\\\\\')|[^\\''\\n\\r])*'","gm"),css:"string"},{regex:new RegExp("\\b\\d+\\.?\\w*","g"),css:"number"},{regex:new RegExp(this.GetKeywords($),"gm"),css:"keyword"},{regex:new RegExp(this.GetKeywords(_),"gm"),css:"special"}];this.CssClass="dp-py";this.Style=".dp-py .builtins { color: #ff1493; }"+".dp-py .magicmethods { color: #808080; }"+".dp-py .exceptions { color: brown; }"+".dp-py .types { color: brown; font-style: italic; }"+".dp-py .commonlibs { color: #8A2BE2; font-style: italic; }"};dp.sh.Brushes.Python.prototype=new dp.sh.Highlighter();dp.sh.Brushes.Python.Aliases=["py","python"];dp.sh.Brushes.Ruby=function(){var $="alias and BEGIN begin break case class def define_method defined do each else elsif "+"END end ensure false for if in module new next nil not or raise redo rescue retry return "+"self super then throw true undef unless until when while yield",_="Array Bignum Binding Class Continuation Dir Exception FalseClass File::Stat File Fixnum Fload "+"Hash Integer IO MatchData Method Module NilClass Numeric Object Proc Range Regexp String Struct::TMS Symbol "+"ThreadGroup Thread Time TrueClass";this.regexList=[{regex:dp.sh.RegexLib.SingleLinePerlComments,css:"comment"},{regex:dp.sh.RegexLib.DoubleQuotedString,css:"string"},{regex:dp.sh.RegexLib.SingleQuotedString,css:"string"},{regex:new RegExp(":[a-z][A-Za-z0-9_]*","g"),css:"symbol"},{regex:new RegExp("(\\$|@@|@)\\w+","g"),css:"variable"},{regex:new RegExp(this.GetKeywords($),"gm"),css:"keyword"},{regex:new RegExp(this.GetKeywords(_),"gm"),css:"builtin"}];this.CssClass="dp-rb";this.Style=".dp-rb .symbol { color: #a70; }"+".dp-rb .variable { color: #a70; font-weight: bold; }"};dp.sh.Brushes.Ruby.prototype=new dp.sh.Highlighter();dp.sh.Brushes.Ruby.Aliases=["ruby","rails","ror"];dp.sh.Brushes.Sql=function(){var _="abs avg case cast coalesce convert count current_timestamp "+"current_user day isnull left lower month nullif replace right "+"session_user space substring sum system_user upper user year",$="absolute action add after alter as asc at authorization begin bigint "+"binary bit by cascade char character check checkpoint close collate "+"column commit committed connect connection constraint contains continue "+"create cube current current_date current_time cursor database date "+"deallocate dec decimal declare default delete desc distinct double drop "+"dynamic else end end-exec escape except exec execute false fetch first "+"float for force foreign forward free from full function global goto grant "+"group grouping having hour ignore index inner insensitive insert instead "+"int integer intersect into is isolation key last level load local max min "+"minute modify move name national nchar next no numeric of off on only "+"open option order out output partial password precision prepare primary "+"prior privileges procedure public read real references relative repeatable "+"restrict return returns revoke rollback rollup rows rule schema scroll "+"second section select sequence serializable set size smallint static "+"statistics table temp temporary then time timestamp to top transaction "+"translation trigger true truncate uncommitted union unique update values "+"varchar varying view when where with work",A="all and any between cross in join like not null or outer some";this.regexList=[{regex:new RegExp("--(.*)$","gm"),css:"comment"},{regex:dp.sh.RegexLib.DoubleQuotedString,css:"string"},{regex:dp.sh.RegexLib.SingleQuotedString,css:"string"},{regex:new RegExp(this.GetKeywords(_),"gmi"),css:"func"},{regex:new RegExp(this.GetKeywords(A),"gmi"),css:"op"},{regex:new RegExp(this.GetKeywords($),"gmi"),css:"keyword"}];this.CssClass="dp-sql";this.Style=".dp-sql .func { color: #ff1493; }"+".dp-sql .op { color: #808080; }"};dp.sh.Brushes.Sql.prototype=new dp.sh.Highlighter();dp.sh.Brushes.Sql.Aliases=["sql"];dp.sh.Brushes.Vb=function(){var $="AddHandler AddressOf AndAlso Alias And Ansi As Assembly Auto "+"Boolean ByRef Byte ByVal Call Case Catch CBool CByte CChar CDate "+"CDec CDbl Char CInt Class CLng CObj Const CShort CSng CStr CType "+"Date Decimal Declare Default Delegate Dim DirectCast Do Double Each "+"Else ElseIf End Enum Erase Error Event Exit False Finally For Friend "+"Function Get GetType GoSub GoTo Handles If Implements Imports In "+"Inherits Integer Interface Is Let Lib Like Long Loop Me Mod Module "+"MustInherit MustOverride MyBase MyClass Namespace New Next Not Nothing "+"NotInheritable NotOverridable Object On Option Optional Or OrElse "+"Overloads Overridable Overrides ParamArray Preserve Private Property "+"Protected Public RaiseEvent ReadOnly ReDim REM RemoveHandler Resume "+"Return Select Set Shadows Shared Short Single Static Step Stop String "+"Structure Sub SyncLock Then Throw To True Try TypeOf Unicode Until "+"Variant When While With WithEvents WriteOnly Xor";this.regexList=[{regex:new RegExp("'.*$","gm"),css:"comment"},{regex:dp.sh.RegexLib.DoubleQuotedString,css:"string"},{regex:new RegExp("^\\s*#.*","gm"),css:"preprocessor"},{regex:new RegExp(this.GetKeywords($),"gm"),css:"keyword"}];this.CssClass="dp-vb"};dp.sh.Brushes.Vb.prototype=new dp.sh.Highlighter();dp.sh.Brushes.Vb.Aliases=["vb","vb.net"];dp.sh.Brushes.Xml=function(){this.CssClass="dp-xml";this.Style=".dp-xml .cdata { color: #ff1493; }"+".dp-xml .tag, .dp-xml .tag-name { color: #069; font-weight: bold; }"+".dp-xml .attribute { color: red; }"+".dp-xml .attribute-value { color: blue; }"};dp.sh.Brushes.Xml.prototype=new dp.sh.Highlighter();dp.sh.Brushes.Xml.Aliases=["xml","xhtml","xslt","html","xhtml"];dp.sh.Brushes.Xml.prototype.ProcessRegexList=function(){function B(_,$){_[_.length]=$}var $=0,A=null,_=null;this.GetMatches(new RegExp("(&lt;|<)\\!\\[[\\w\\s]*?\\[(.|\\s)*?\\]\\](&gt;|>)","gm"),"cdata");this.GetMatches(new RegExp("(&lt;|<)!--\\s*.*?\\s*--(&gt;|>)","gm"),"comments");_=new RegExp("([:\\w-.]+)\\s*=\\s*(\".*?\"|'.*?'|\\w+)*|(\\w+)","gm");while((A=_.exec(this.code))!=null){if(A[1]==null)continue;B(this.matches,new dp.sh.Match(A[1],A.index,"attribute"));if(A[2]!=undefined)B(this.matches,new dp.sh.Match(A[2],A.index+A[0].indexOf(A[2]),"attribute-value"))}this.GetMatches(new RegExp("(&lt;|<)/*\\?*(?!\\!)|/*\\?*(&gt;|>)","gm"),"tag");_=new RegExp("(?:&lt;|<)/*\\?*\\s*([:\\w-.]+)","gm");while((A=_.exec(this.code))!=null)B(this.matches,new dp.sh.Match(A[1],A.index+A[0].indexOf(A[1]),"tag-name"))}
//}}}
!Workflow of ~HaikuVM
The basic idea behind ~HaikuVM is pretty simple. ~HaikuVM uses javac to generate class files and then post processes them a bit. The resulting class files turn into data, stuffed in C structures that you compile and bundle with the Haiku JVM and the system libraries to get an executable program (in the case of the Arduino, a hex file). All parts are compiled by a C cross compiler for your target platform. During runtime the Haiku VM interpretes the JAVA byte code, stored in the C data structures mentioned above. So ~HaikuVM will not (and is not designed to) load class files after C compilation is done.

[img[images/overview.png]]
!!step one (java to class)
Translate your JAVA program with [[haikuc]] into a class-file (bytecode). This will translate the JAVA class given by you. From this seed it recursively determines which classes and class members are used. All other classes and class members are discarded. For this job [[haikuc]] uses javac. But it will not compile against rt.jar (the standard JAVA runtime). Instead it will use the leJOS runtime which is given in classes.jar. Superseded by haikuRT, to pick and overwrite a specific small set of this leJOS runtime classes to adapt to ~HaikuVM and micros.
!!step two (class to C)
Basically [[haikulink]] will read the bytecode (using the BCEL library) and translate it into C data structures. In contrast, other systems e.g. GCJ will translate direct into C program code. With Haiku the only C code is the C code of the Haiku virtual machine (Haiku VM) itself augmented with C data structures.  Together this is linked into the binary by [[haikulink]]. During runtime (e.g. in an Atmega8) the Haiku VM interpretes the data in the (above mentioned) C data structures.  ([[More ...|Compact HaikuVM Code]])
!!step three (C to binary)
Because [[haikulink]] translated into C code we now need to cross-compile it for the target machine. This is in contrast to leJOS (and ~NanoVM) where no cross-compiling step is needed. On the other hand cross-compiling allows a tight coupling of the above C data structures and the Haiku VM. In addition the linker step will eliminate all unneeded code and data. This is the main reason for having surprisingly short binaries representing your JAVA program.
!!step four (upload and run)
[[haikuupload]] uploads the binary builded in step three, to the microprocessor.
!Philosopie of ~HaikuVM
~HaikuVM tries to use as less as possible native methods. (Native methods are methods which have to be written in C.) The idea is to reduce (not restrict) the native methods to the following small set:
A) reading from and writting to RAM memory like this:
*public static native int  getMemory8(int adr);
*public static native void setMemory8(int adr, int value);
*... about 10 more memory setter and getter methods
B) A method for getting the time in milliseconds:
*public static native long currentTimeMillis();
C) A method for copying arrays:
*public static native void arraycopy(Object src, int srcPos, Object dest, int destPos, int length);
D) And methods for Thread schedule:
*private native int fork();
*private native int setStateAndSwitch(int state);
Before a simple ~HalloWorld Java program like this:
<code java>
public class HelloWorld {
    public static void main(String[] args) {
        System.out.println("Hello World");
    }
}
</code>
will run on a micro you have to initialize several things. This boilerplate code for basic initialization have to be written for each Java program you write. Typically you have to write code for:
* initialize serial output (baud rate etc.).
* code a basic write(aByte) and readByte() method.
* initialize a time base.
* write an exception handler.

You will find different approaches for this. Here I list only three:
#Write code for initialization in your Java program<br>This is flexible when adapting to different ~AVRs but pollutes your Jave code.
#Write code for initialization in C, right into Haiku VM's C code<br>This has to be specific for an AVR model and could be done for every AVR with a big #if. But then it's easy to forget a specific AVR or initialisation aspect and, for new micros, you are forced to write C code. In this concern it's an inflexible approach but, at the end, does not pollute your Java code.
#Write code for initialization in C, using JNI functionality<br>This is a variant of the above alternative.

Here I give you an example for the first approach:  initialization (of an Arduino Duemilanove) in your Java program:
<code java>
package arduino.tutorial;

import static haiku.avr.AVRConstants.*;

public class HelloWorldWithoutHaikuKernel {
    private static final int BAUD_RATE = 57600;
    private static final long F_CPU = 16000000;

    private static void init() {
        // set baud rate
        final short t = (short) (((F_CPU >> 4) + (BAUD_RATE >>> 1)) / BAUD_RATE - 1);
        UBRR0H = (t >>> 8);
        UBRR0L = t;
        UCSR0B = (1 << RXEN0) | (1 << TXEN0);
    }

    private static void write(int b) {
        while ((UCSR0A & (1 << UDRE0)) == 0)
            ;

        UDR0 = b;
    }

    public static void println(String line) {
        for (int i = 0; i < line.length(); i++) {
            write(line.charAt(i));
        }
        write('\r');
        write('\n');
    }

    public static void main(String[] args) {
        init();
        println("Hello World");
        while(true) ;
    }
}
</code>
Because no timer methods are needed and no exceptions are thrown the code for initializing this is neglegted. At least this program is complete and will print "Hello World" on an Arduino Duemilanove. But it includes all the things which are needed to configure an Arduino Duemilanove for this job. Due to this fact it is not portable to other micros.

|bgcolor(#6f6): ~HelloWorldWithoutHaikuKernel<br><br><br><br> |
|bgcolor(#66b): The Haiku VM<br> |
|bgcolor(#b66): Hardware: Duemilanove  |
| Your "Hello World" program is specific for Duemilanove  |c

~HaikuVM follows an ''innovative third'' approach by introducing a ''~MicroKernel''. The idea is that the ~MicroKernel, written in Java, should cover all the target micro specific initialization code. So the C part of ~HaikuVM can kept more generic and free from model specific C code. (With the intention that nobody is forced to write C code for a new micro.) While your main Java program can be expressed without being polluted by boilerplate code for specific AVR initialization.

Factoring out initialisation code from ~HelloWorldWithoutHaikuKernel into a ~HaikuKernel looks like this for an Arduino Duemilanove:
<code java>
package arduino.tutorial;

import static haiku.avr.AVRConstants.*;
import java.io.*;

public class HaikuKernel {
    private static final int BAUD_RATE = 57600;
    private static final long F_CPU = 16000000;

    private static void init() {
        // set baud rate
        final short t = (short) (((F_CPU >> 4) + (BAUD_RATE >>> 1)) / BAUD_RATE - 1);
        UBRR0H = (t >>> 8);
        UBRR0L = t;
        UCSR0B = (1 << RXEN0) | (1 << TXEN0);
        
        // set timer 0 prescale factor to 64
        TCCR0B = (1<<CS01)  | (1<<CS00);
        
        // enable timer 0 overflow interrupt
        TIMSK0 = (1<<TOIE0);

        System.out = new PrintStream(new OutputStream() {
            public void write(int b) throws IOException {
                while ((UCSR0A & (1 << UDRE0)) == 0)
                    ;

                UDR0 = b;
            }
        });
    }

    public static void main(String[] args) {
        init();
        haiku.vm.HaikuMagic.main(args); // attention, attention, here is some magic
        Thread.currentThread().stop();
    }
}
</code>
In conjunction with this ~HaikuKernel you are ready to use the ''now portable'' ~HelloWorld program from the begin of this tutorial. For this you have to configure this ~HaikuKernel  in '~HaikuVM.properties' to be used with your configuration. Then HaikuVM will start your ~MicroKernel first. Then the ~MicroKernel will start your program. For this you may have noticed line 35. Line 35 leading us to some ''Haiku magic''. The magic here is that [[haikulink]] will substitute the call of ''haiku.vm.~HaikuMagic.main(args)'' by the call of your Java main method. In this tutorial effectively resulting in a call of ''~HelloWorld.main(args)'' during linktime.

|bgcolor(#6f6): ~HelloWorld<br> |
|bgcolor(#6b6): <br>~MicroKernel: ~HaikuKernel for Duemilanove<br><br><br> |
|bgcolor(#66b): The Haiku VM<br> |
|bgcolor(#b66): Hardware: Duemilanove  |
| Only the ~MicroKernel is specific for Duemilanove  |c

Now your program (and others) runs unchanged on an Arduino Leonardo. (And you only have to write a Microkernel for a micro once.)

|bgcolor(#6f6): ~HelloWorld<br> |
|bgcolor(#6b6): <br>~MicroKernel: ~HaikuKernel for Leonardo<br><br><br> |
|bgcolor(#66b): The Haiku VM<br> |
|bgcolor(#b66): Hardware: Leonardo |
| Only the ~MicroKernel is specific for Leonardo |c


The download of ~HaikuVM includes predefined ~HaikuKernels for several AVR models and platforms. If yours is missing and you designed a ~HaikuKernel for it, please send it to me. I will include it in future versions of ~HaikuVM.


Advantages of using a ~MicroKernel:
* no need for JNI code to initialize your AVR.
* full flexibility in Java having no need to switch to C.
* initialization code written in Java ~MicroKernels tends to be 4 times shorter than equivalent C code (see [[Compact]]).
* exception handler is seamingly integrated in the general exception handling of Java.

To be continued ...
Blink is the "Hello World" for microcontroller. The primary goal of Blink is to let a LED blink, which is connected with one of the pins of the microcontroller in focus. All examples given here, assume that you use a microcontroller based on ~ATmega328p.

!~BlinkSimple

If you are a beginner or faced with the fact having a microcontroller not supported by ~HaikuVM yet, then this is a good starting point. For ~BlinkSimple.java, only the pure minimum of preconditions for running a ~HaikuVM program are need to be fullfilled. Especialy timing and serial IO is no precondition for ~BlinkSimple.

~BlinkSimple assumes that the LED is connected with Port B and Bit 5. The ''manual for ~ATmega328p'' states that you need register DDRB to set the ~IN- or OUTPUT direction of every pin of PORTB. Here we set pin 5 to output. To have direct memory access to the underlying 8 Bit C Variables DDRB and PORTB we have to declare them and annotate them as @~NativeCVariable8 (see chapter [[Memory Access]]).

<code java>
import haiku.vm.NativeCVariable8;

public class BlinkSimple {
    @NativeCVariable8
    private static volatile int DDRB;
    
    @NativeCVariable8
    private static volatile int PORTB;

    private static final int LED = 1 << 5;

    private static void delay(int nounit) {
        while(nounit>0) {
            nounit--;
        }
    }

    public static void main(String[] args) {
        // Data direction of I/O-Port.
        DDRB = LED; // set pin 5 to output
        while (true) {
            PORTB |= LED; // on
            delay(3000);
            PORTB &= ~LED; // off
            delay(3000);
        }
    }
}
</code>

~BlinkSimple can be started like this (provided you installed ~HaikuVM in C:\haikuVM):
<code bash>
mkdir myProject 
cd myProject 
C:\haikuVM\bin\haiku -v --Config avr -o BlinkSimple.hex C:\haikuVM\examples\src\main\java\avr\tutorial\BlinkSimple.java
</code>

So far so simple. But we can do better. The problem with ~BlinkSimple is the delay-function.We just have a loop wasting some CPU cycles (busy wait).  And we don't have any time units. What we really want, is a blink intervall of 3000 milli seconds. To accomplish this we have to setup proper timing.

!Blink

Next we want to use Thread.sleep(..) for the delay-function. For this we have to setup proper timing. In this tutorial all you have to know is that timing is done via timer 0 overflow interrupt. (For more details on timing see [[Tutorial Timing]].)  You have to set timer 0 prescale factor to 64 and enable timer 0 overflow interrupt. The timer 0 overflow interrupt itself is already part of the Haiku VM code (and assumes a prescale factor of 64). So you don't have to care about this now. To find the proper registers to set you have to take a look into the ''manual for ~ATmega328p''. We have to use register ~TCCR0B to set the prescale factor and ~TIMSK0 to enable the interrupt.

<code java>
package avr.tutorial;

import haiku.vm.NativeCVariable8;

public class Blink {
    @NativeCVariable8
    private static volatile int TCCR0B;
    private static final int CS00 = 0;
    private static final int CS01 = 1;
    private static final int CS02 = 2;
    private static final int WGM02 = 3;
    private static final int FOC0B = 6;
    private static final int FOC0A = 7;

    @NativeCVariable8
    private static volatile int TIMSK0;
    private static final int TOIE0 = 0;
    private static final int OCIE0A = 1;
    private static final int OCIE0B = 2;

    @NativeCVariable8
    private static volatile int PORTB;

    @NativeCVariable8
    private static volatile int DDRB;
    
    private static final int LED = _BV(5);

    private static void initAtmega328p_16MHz() {
        // set timer 0 prescale factor to 64
        // for correct millisecond timing of:
        // Atmega328p 16MHz
        TCCR0B |= _BV(CS01) | _BV(CS00);

        // enable timer 0 overflow interrupt
        // important for:
        // Thread.sleep(ms)
        // System.currentTimeMillis()
        TIMSK0 |= _BV(TOIE0);
    }

    private static void delay(int ms) {
        try {
            Thread.sleep(ms);
        } catch (InterruptedException e) {
        }
    }

    public static int _BV(int bit) {
        return 1 << bit;
    }

    public static void main(String[] args) {
        initAtmega328p_16MHz();

        // Data direction of I/O-Port.
        DDRB = LED;
        while (true) {
            PORTB |= LED; // on
            delay(3000);
            PORTB &= ~LED; // off
            delay(3000);
        }
    }
}
</code>

Blink can be started like this (provided you installed ~HaikuVM in C:\haikuVM):
<code bash>
mkdir myProject 
cd myProject 
C:\haikuVM\bin\haiku -clean -v --Config duemilanove C:\haikuVM\examples\src\main\java\avr\tutorial\Blink.java
</code>
~~Here I use option -clean just to make sure that files, possible left from the previous example, are deleted to not interfere with this Blink example.~~

!Blinky

Can we do better. Yes, we can. All this native variable declarations are already done for you in 'haiku.avr.~AVRConstants.java'. So, if we import this, the code become more compact.

<code java>
package avr.tutorial;

import static haiku.avr.AVRConstants.*;

public class Blinky {
    // LED is connected with PORTB and Bit 5.
    // give it a name:
    private static final int LED = 1 << 5;

    private static void initAtmega328p_16MHz() {
        // set timer 0 prescale factor to 64
        // for correct millisecond timing of:
        // Atmega328p 16MHz
        TCCR0B |= (1<<CS01) | (1<<CS00);

        // enable timer 0 overflow interrupt
        // important for:
        // Thread.sleep(ms)
        // System.currentTimeMillis()
        TIMSK0 |= (1<<TOIE0);
    }

    public static void main(String[] args) throws InterruptedException {
        initAtmega328p_16MHz();

        // initialize the digital pin as an output.
        DDRB |= LED;
        // the loop runs forever:
        while (true) {
            PORTB |= LED;       // turn the LED on (HIGH is the voltage level)
            Thread.sleep(1000); // wait for a second
            PORTB &= ~LED;      // turn the LED off by making the voltage LOW
            Thread.sleep(1000); // wait for a second
        }
    }
}
</code>

Again, Blinky can be started like this (provided you installed ~HaikuVM in C:\haikuVM):
<code bash>
mkdir myProject 
cd myProject 
C:\haikuVM\bin\haiku -clean --Config duemilanove C:\haikuVM\examples\src\main\java\avr\tutorial\Blinky.java
</code>

!~BlinkyWithMicroKernel

Can we do better. Yes, we still can. With the configuration 'duemilanove' comes a ~MicroKernel which is specific for the Duemilanove. Brief, a microkernel is a piece of ''JAVA'' code which function is to initialize the hardware. (See [[Tutorial All About MicroKernels]] to learn more about microkernels. The invention of microkernels, itself written in JAVA, is possibly the biggest invention of HaikuVM.) Now, after the initialization of timer0 is factored out into a ~MicroKernel the code becomes very compact.
<code java>
package avr.tutorial;

import static haiku.avr.AVRConstants.*;

public class BlinkyWithMicroKernel {
    // LED is connected with PORTB and Bit 5.
    // give it a name:
    private static final int LED = 1 << 5;

    public static void main(String[] args) throws InterruptedException {
        // initialize the digital pin as an output.
        DDRB |= LED;
        // the loop runs forever:
        while (true) {
            PORTB |= LED;       // turn the LED on (HIGH is the voltage level)
            Thread.sleep(1000); // wait for a second
            PORTB &= ~LED;      // turn the LED off by making the voltage LOW
            Thread.sleep(1000); // wait for a second
        }
    }
}
</code>

~BlinkyWithMicroKernel can be started like this (provided you installed ~HaikuVM in C:\haikuVM):
<code bash>
mkdir myProject 
cd myProject 
C:\haikuVM\bin\haiku -clean --Config duemilanove C:\haikuVM\examples\src\main\java\avr\tutorial\BlinkyWithMicroKernel.java
</code>

You might be interrested in [[Tutorial Interrupts]], too.
There are many examples in file [[HaikuVM.properties]] for allready configured microcontrollers. If yours is not in the file, start by copying a configuration which closest match your micro and give it a new name. Then adapt the values to your needs.
There might be situations where interaction with an C interrupt routine is wanted. ~HaikuVM, as a JAVA VM, does not support interrupts. Instead, interrupt routines have to be written in C. This can be done for every interrupt, except for the timer 0 overflow interrupt which is reserved for ~HaikuVM's timing. (But is configurable via option [[TimerInterrupt|Command Line Options]].) ''Interrupts are enabled by default in ~HaikuVM.''

It's not the goal of this tutorial to explain interrupts. Here are great tutorials on AVR interrupts:
http://www.avrfreaks.net/index.php?name=PNphpBB2&file=viewtopic&t=55347

In this tutorial I want to show how to interact with a '~TIMER2_OVF_vect' interrupt routine. The timer 2 overflow interrupt is handled in function  '~TIMER2_OVF_vect' mean and lean by just incrementing a variable of type jlong. This is how the C code looks like to accomplish this:
<code cpp>
#include ???
#include <avr/interrupt.h>

volatile static jlong timer2_interrupts = 0;

ISR(TIMER2_OVF_vect) {
    timer2_interrupts ++;
}
</code>

On the other end there is a Java program which wants to read out the value of timer2_interrupts and prints the first 10 values. This is how the Java program looks like (until now):
<code java>
package arduino.tutorial;

import static haiku.avr.AVRConstants.*;

public class InterruptTimer2 {

    private static native long getTimer2();

    public static void main(String[] args) {
        // TODO: set up timer2

        for (int i = 0; i < 10; i++) {
            System.out.println("Value of timer2_interrupts is: " + getTimer2());
        }
    }
}
</code>

As you may have expected, we use a ''native'' Java method to read out the value of timer2_interrupts (see line 07 above). From the [[Tutorial JNI]] we have learned that ''all'' JNI C function wrappers are generated during the [[haikulink]] phase and placed in file './myCProject/haikuC/haikuJNI.c' for cut&past usage. So we pick our getTimer2(..) function wrapper and getTime2(..) JNI template from there and cut&past it into our C file which now becomes:
<code cpp>
#include <jni.h>
#include <avr/interrupt.h>

volatile static jlong timer2_interrupts = 0;

ISR(TIMER2_OVF_vect) {
    timer2_interrupts ++;
}

/**
 * Automatic generated JNI template
 * getTimer2()J
 */
JNIEXPORT jlong Java_avr_tutorial_Interrupt1_getTimer2( JNIEnv *env, jobject obj) {
    // TODO: insert your code here
    return 0;
}

/**
 * Automatic generated JNI wrapper
 * getTimer2()J
 */
JNIEXPORT void native_arduino_tutorial_InterruptTimer2_getTimer2_J(void) {
    pushTop();	// Save variable top onto stack.
    {
        jobject	obj = NULL;
        JNIEnv *env = NULL;
        top.j = Java_arduino_tutorial_InterruptTimer2_getTimer2(env, obj);
    }
    // Variable top holds the return value. But we have to push the lower half.
    pushTop0();
}
</code>
(Don't forget to insert line 01 to include the basic JNI type declarations.)

If you inspect the JNI function '~Java_avr_tutorial_Interrupt1_getTimer2(env, obj)' you will see a TODO which has to be filled. In our case we want to access and return the value of timer2_interrupts:
<code cpp>
#include <jni.h>
#include <avr/interrupt.h>

volatile static jlong timer2_interrupts = 0;

ISR(TIMER2_OVF_vect) {
    timer2_interrupts ++;
}

/**
 * Automatic generated JNI template
 * getTimer2()J
 */
JNIEXPORT jlong Java_arduino_tutorial_InterruptTimer2_getTimer2(JNIEnv *env, jobject obj) {
    jlong value;
    uint8_t oldSREG = SREG;
    cli(); // we don't want to be desturbed by an interrupt
    value = timer2_interrupts;
    SREG = oldSREG; // restore interruptable state again.
    return value;
}

/**
 * Automatic generated JNI wrapper
 * getTimer2()J
 */
JNIEXPORT void native_arduino_tutorial_InterruptTimer2_getTimer2_J(void) {
    pushTop();	// Save variable top onto stack.
    {
        jobject	obj = NULL;
        JNIEnv *env = NULL;
        top.j = Java_arduino_tutorial_InterruptTimer2_getTimer2(env, obj);
    }
    // Variable top holds the return value. But we have to push the lower half.
    pushTop0();
}
</code>
(See also './haikuVM/myCProject/tutorials/interruptTimer2.c').

There is only a final step missing. We have to initialize timer 2 and its overflow interrupt (here for ~ATmega328p) . In this example its done in the Java main(..) method of our example (see also 'arduino.tutorial/~InterruptTimer2.java'):
<code java>
package arduino.tutorial;

import static haiku.avr.AVRConstants.*;

public class InterruptTimer2 {

    private static native long getTimer2();

    public static void main(String[] args) {
        // prescaler 1024
        TCCR2B = (1<<CS22) | (1<<CS21) | (1<<CS20);

        // enable timer interrupt overflow
        TIMSK2 = (1<<TOIE2);

        for (int i = 0; i < 10; i++) {
            System.out.println("Value of timer2_interrupts is: " + getTimer2());
        }
    }
}
</code>

Have fun when playing with different prescale values!

*[[JNI simple]]
*[[JNI enhanced]]
*[[JNI using functions from a C library]]
*[[JNI using functions from a C library using annotations]]
*[[JNI field access]]
Here are great tutorials on AVR timers:
http://www.avrfreaks.net/index.php?name=PNphpBB2&file=viewtopic&t=50106
This tutorial on timing in ~HaikuVM compliments those. Those tutorials are aimed at the C language, here I'll give some insight on how ~HaikuVM uses the AVR's timers.

First of all, the VM of Haiku (written in C) does not set or configure any timer, it's up to your Java program to do that. Many simple C and therefore Java programs do work without the use of timers. 

On the other hand, when you start to use some of Java's time methods like 
*Thread.sleep(..), 
*Thread.wait(..), 
*System.currentTimeMillis()
*Or you want to use multiple Threads 
then ''a proper setup of timer 0 is important''. The VM of Haiku (for ~AVRs) is designed in a way that proper timing relies on timer 0 overflow interrupt. The timer 0 overflow interrupt is handled in an already predefined interrupt routine '~TIMER0_OVF_vect' (located in file './haikuVM/simpleOS.c') and just increments variable 'timer0_interrupts'. From this variable the function millis() derives the milliseconds for Thread.sleep(..), Thread.wait(..), etc. and for Thread scheduling. Here is some C-code, to give you a clue:
<code cpp>
volatile jmillis timer0_interrupts = 0;
...
SIGNAL(TIMER0_OVF_vect)
{
    timer0_interrupts++;
}
...
julong millis()
{
    jmillis m;
    uint8_t oldSREG = SREG;
    cli();
    m = timer0_interrupts;
    SREG = oldSREG;
    return m * HAIKU_MillisDividend / HAIKU_MillisDivisor;
}
</code>
Where ''~HAIKU_MillisDividend'' and ''~HAIKU_MillisDivisor'' are #defines (see file 'haikuDefs.h') and those values will be pre-calculated automatically during the [[haikulink]] phase derived from HaikuVM property Clock (see [[HaikuVM.properties]]). The values for ''~HAIKU_MillisDividend'' and ''~HAIKU_MillisDivisor'' are calculated in a way to produce an interrupt every millisecond as close as possible (assuming a prescaler of 64 for timer 0). See the table below. If, for some reasons, you don't want to live with the predefined values or you want to use a different prescale you have to define your values manually in file '~HaikuVM.properties' like this:
<code bash>
myconfig.MillisDividend = 128
myconfig.MillisDivisor = 125
</code>
Where "myconfig" is the Config-parameter you choose in the commandline of [[haikulink]] or [[haiku]].

This is a snipped showing how you setup the timer 0 with a prescale of 64 and enable timer 0 overflow interrupt for an Atmega8, Atmega16,  etc.:
<code java>
import static haiku.avr.AVRConstants.*;
...
// In main():
        // Timer-Configuration: Prescaler to 1/64
        TCCR0 |= (1 << CS01);
        TCCR0 |= (1 << CS00);
        // Timer-Overflow-Interrupt-Enable Timer0
        TIMSK |= (1 << TOIE0); 
...
</code>

This is a snipped showing how you setup the timer 0 with a prescale of 64 and enable timer 0 overflow interrupt for an Atmega328p,  etc.:
<code java>
import static haiku.avr.AVRConstants.*;
...
// In main():
        TCCR0B |= _BV(CS01) | _BV(CS00); // set prescaler to 1/64
        TIMSK0 |= _BV(TOIE0); // Timer0-Overflow-Interrupt-Enable
...
</code>

For a complete, running Java example which sets up timer 0 for ~ATmega328p take a look at 'C:\haikuVM\examples\src\main\java\avr\tutorial\Blink.java' and/or here [[Tutorial Blink]].

Here is a table, presenting what  ''~MillisDividend'' and ''~MillisDivisor'' ~HaikuVM will calculate and assign automatically (in blue) for some commonly used Clock values [Hz], if  ~HAIKU_MillisDividend and ~HAIKU_MillisDivisor are not configured manually.
| Clock [Hz] | Prescale | ~MillisDividend | ~MillisDivisor | Error in [ms/s] | Overflow32 [min] | Resolution [ms] |
| 8000000 | 1| 4 | 125 |0.00000 | 572.662 | 0.0320000 |
|~| 8| 32 | 125 |0.00000 | 572.662 | 0.256000 |
|~| 64|bgcolor(#66f):  256 |bgcolor(#66f):  125 |0.00000 | 572.662 | 2.04800 |
|~| 256| 1024 | 125 |0.00000 | 572.662 | 8.19200 |
|~| 1024| 2261 | 69 |0.00353827 | 1037.43 | 32.7681 |
||||||||
| 12000000 | 1| 8 | 375 |0.00000 | 190.887 | 0.0213333 |
|~| 8| 64 | 375 |0.00000 | 190.887 | 0.170667 |
|~| 64|bgcolor(#66f): 512 |bgcolor(#66f): 375 |0.00000 | 190.887 | 1.36533 |
|~| 256| 2048 | 375 |0.00000 | 190.887 | 5.46133 |
|~| 1024| 2119 | 97 |0.00125846 | 737.967 | 21.8454 |
||||||||
| 15000000 | 1| 32 | 1875 |0.00000 | 38.1775 | 0.0170667 |
|~| 8| 256 | 1875 |0.00000 | 38.1775 | 0.136533 |
|~| 64|bgcolor(#66f): 2048 |bgcolor(#66f): 1875 |0.00000 | 38.1775 | 1.09227 |
|~| 256| 2853 | 653 |-0.000186938 | 109.621 | 4.36907 |
|~| 1024| 367 | 21 |-0.00435965 | 3408.70 | 17.4762 |
||||||||
| 16000000 | 1| 2 | 125 |0.00000 | 572.662 | 0.0160000 |
|~| 8| 16 | 125 |0.00000 | 572.662 | 0.128000 |
|~| 64|bgcolor(#66f): 128 |bgcolor(#66f): 125 |0.00000 | 572.662 | 1.02400 |
|~| 256| 512 | 125 |0.00000 | 572.662 | 4.09600 |
|~| 1024| 2048 | 125 |0.00000 | 572.662 | 16.3840 |
||||||||
| 20000000 | 1| 8 | 625 |0.00000 | 114.532 | 0.0128000 |
|~| 8| 64 | 625 |0.00000 | 114.532 | 0.102400 |
|~| 64|bgcolor(#66f): 512 |bgcolor(#66f): 625 |0.00000 | 114.532 | 0.819200 |
|~| 256| 2048 | 625 |0.00000 | 114.532 | 3.27680 |
|~| 1024| 367 | 28 |-0.00435965 | 2556.53 | 13.1071 |
*Overview
**[[Tool Chain]]
**[[Architecture]]
**[[Your Project on Disk and at Runtime]]
*Tutorials
**[[Tutorial Blink]]
**[[Tutorial Timing]]
**[[Tutorial Basic Serial IO]]
**[[Tutorial Use Your Own C main Function]]
**[[Tutorial JNI]]<<tiddler [[Tutorial JNI]]>>
**[[Tutorial Interrupts]]
**[[Tutorial All About MicroKernels]]
**[[Tutorial How to configure micro controllers currently not supported in file HaikuVM.properties]]
**[[Tutorial Direct Memory Access|Memory Access]]
**[[Tutorial Memory Layout of HaikuVM Objects|Memory Layout of HaikuVM Objects]]
**[[Different Targets|Runs on AVR ATmega8, AVR ATmega328p (and Windows, UNIX)]]
***[[Arduino]]
***[[ATmega32u4|Leonardo]]
***[[Processing]]
***[[Asuro]]
***[[Windows|Visual Studio]]
***[[LINUX|Ubuntu]]
*~IDEs
**[[Eclipse]]
**[[Arduino IDE]]
If you want to get a first impression about ~HaikuVM but you don't have a microcontroller, here is a way to get it.
If you have Ubuntu (tested with 12.04) you just enter:
<code bash>
cd /home/bob/haikuVM/myCProject  
/home/bob/haikuVM/bin/haiku -v --Config unix /home/bob/haikuVM/examples/src/main/java/arduino/tutorial/HelloWorldJava.java
</code>

<<tiddler chmod>>
If you want to get a first impression about ~HaikuVM but you don't have a microcontroller, here is a way to get it.
If you have MS Windows and Visual Studio (tested with ''Visual Studio 8'' and ''Visual Studio 10 Express'') you have  to open the 'Visual Studio Console'. Here you just enter:
<code bash>
cd C:\haikuVM\myCProject  
C:\haikuVM\bin\haiku -v --Config pc C:\haikuVM\examples\src\main\java\arduino\tutorial\HelloWorldJava.java 
</code>
~HaikuVM is a JAVA VM for micro controllers. It implements all JAVA byte codes (without "invokedynamic").

~HaikuVM has been started for hobbyists who develop applications for ~AVRs (e.g. ARDUINO) to open the world of JAVA.
''Yes, with ~HaikuVM you can program any ARDUINO with JAVA!'' ([[More ...|Processing]])

~HaikuVM is so small that it even runs on an atmega8 (and the ASURO robot).
''And yes, you can program an ASURO robot with JAVA!'' ([[More ...|Asuro]])

But for the beginner I suggest to start with a simple and basic AVR example. ([[More ...|BlinkSimple]])

~HaikuVM works by compiling JAVA byte code to C data structures to be compiled by a C cross compiler for your [[target|Runs on AVR ATmega8, AVR ATmega328p (and Windows, UNIX)]] platform. So, the resulting code is small and fast. ([[More ...|Tool Chain]]) 

[img[images/overview.png]]
For further details take a look [[here|Architecture]].
If you want to zoom into details on Flash and RAM usage take a look at [[this|Your Project on Disk and at Runtime]] page.
(unordered)
*Integrate a scripting language like FORTH.
*Seamless integration with C++ objects. (Currently I'm attracted to the idea of [[SWIG|http://www.swig.org/Doc1.3/Java.html#imclass]].)
*Implement a compacting garbage collector to solve possible fragmentation.
*Enable runtime debugging.
*Seamless integration with interrupts (~ISRs). This is, handling Interupts in Java.
*Integration of bytecode optimization by using the open source tool [[ProGuard|http://proguard.sourceforge.net/]].
*Ahead of time Compiler (into C++ code) instead using the bytecode interpreter (space vs. time).
*Support for ~NetBeans IDE.
*String constants stay in flash memory (and are never copied to RAM when used).
* Threads with different priority
!On the Disk
You have to move (cd) into an empty directory which will be used for your project. Any empty directory will do. In addition, ~HaikuVM comes with a template directory called 'myCProject' for your project (and tutorials). At the beginning, and to follow the examples and tutorials more literally, I suggest to pick this one.
*''myCProject/'' (Any other name and (initial) ''empty'' directory, elsewhere on your disk, will do as well.)<br>During a run of haikulink directories will be created here. (Some only once.)
**''~HaikuVM/''<br>The Java VM (see [[Architecture]]).
**''~HaikuVM/utility/''<br>Mainly constants and static variables including method- and exception-tables as derived from your Java program. Other stuff like JNI function templates and debug information:
***Table of constants (''haikuConfig.c'', ''haikuConfig.h'')
***Table of exceptions, table of functions (''haikuConfig.c'', ''haikuConfig.h'')
***Bytecode as prepared and linked for the Haiku VM. "Bytecode" here has to be translated to [["initialized C structs"|Compact HaikuVM Code]].
****C structs initializing a class description and all methods bytecode. (''haikuJava.c'')
****C structs describing the memory layout of objects and methods. (''haikuJava.h'')
***Bytecode map to function labels (''bytecodeDispatcher.h'')
***JNI code (standard) and ~HaikuVM native C functions support (''haikuJNI.c'' and ''~NativeCFunctions.cpp'')
**''~HaikuVM/examples/~HaikuVM/''<br>Contains a generic ino-file just in case, to be compatible with the [[Arduino IDE]] as well.
**''target/cross/''<br>Contains all stuff needed for 'make' to cross compile your project.
!On the Microcontroller
!!Flash usage
Here is a diagram to give you an impression about how flash memory is used from ~HaikuVM. This is only a rough estimate about the relation of the sections mentioned below. The concret layout (and order) is not important for ~HaikuVM and is up to the (AVR) linker.
|e| possible unused |
|e|~|
|e|~|
|e|~|
|e|~|
|d|bgcolor(#6f6): Your Java Program |
|d|~|
|d|~|
|d|~|
|c|bgcolor(#6d6): Your ~MicroKernel (possible empty) |
|b|bgcolor(#6b6): Constants and exception tables |
|a|bgcolor(#66b): The Haiku VM |
|a|~|
| flash usage |c

*''Section [a] The Haiku VM''<br>This section corresponds to the project directory '~HaikuVM'. It contains the C program which in fact is the Haiku VM (the equivalent to the Java VM). Although the sourcecode of ~HaikuVM has constant size, the resulting flash memory consumption of section [a-b] depends of your Java program. This is because ~HaikuVM is designed in a way that the AVR linker is able to pick only the source code needed. For example if you don't use double devision the bytecode DDIV (which divides two doubles) is not linked into the flash image. (And therefore saves space.)
*''Section [b] Constants and exception tables''<br>This section corresponds to the project directory '~HaikuVM/utility'.
*''Section [c] Your [[MicroKernel | Tutorial All About MicroKernels]] (possible empty)''<br>This section corresponds to the project directory '~HaikuVM/utility'. This is only a logical section. Physically it's completely merged with section [d].
*''Section [d] Your Java Program''<br>This section corresponds to the project directory '~HaikuVM/utility' and contains the bytecode (as refined by haikulink) of your Java Program.
!!RAM usage
|C|bgcolor(#6f6): Java stack and object heap |
|C|~|
|C|~|
|C|~|
|C|~|
|B|bgcolor(#6d6): Java static variables |
|A|bgcolor(#66b): C stack (ABI) and variables for the Haiku VM |
| RAM usage |c

*''Section [A] C stack (ABI) and variables for Haiku VM''<br>This section defines the space which is needed for the plain Haiku VM to do its job. This stack corresponds in no way with the Java [[stack|Stack Layout]].
*''Section [B] Java static variables''<br>This section defines the space for the Java static variables your Java program (section [c] + [d]) is using.
*''Section [C] Java stack and object heap''<br>This area consists entirely of Java objects and is subject to garbage collection.

''Note''
The size of section [B] + [C] is defined by your ~HaikuVM property ''Memory'' as declared in [[HaikuVM.properties]] of your configuration. The rest of the RAM is used by section [A]. Please select ~HaikuVM property ''Memory'' in a way that section [A] has room to live. In my experience 300 byte is enough (for an Atmega328p).

For being portable, I decided to code the VM in pure C (no assembler and no C++).
On Linux, if the first time, don't forget to change shell scripts to have execute permission like this:
<code bash>
chmod +x haikuVM/bin/*
</code>
On some compilers (e.g. winavr / gcc-avr) the JAVA type ''double'' is mapped to C type ''float''.
~HaikuVM supports double and float types. But details depend on the underlying hardware and C compiler infrastructure. Because ~HaikuVM works by translating JAVA bytecode to C code. So, for instance, the WINAVR C Compiler supports double and float types but the double type has only 32 Bits and is, behind the scenes, effectively a C float type.
!link, upload and run a program
Usage: 
haiku [options] main-class

Example: 
<code bash>
haiku -v HelloWorld 
</code>
The haiku command links and uploads a JAVA program. It is the equivalent of haikulink followed by haikuupload.

Any of the options for haikulink and haikuupload can be specified.

The default binary name is <main-class>.hex, e.g. Tune.hex.
!compile a JAVA program
Compiles one or more java files.

Usage: haikuc <java-files>
Example: 
<code bash>
haikuc HelloWorld.java
</code>
Internally haikuc calls javac with parameters:
-bootclasspath <path to haikuRT and classes.jar> <java-files>

-bootclasspath is set because ~HaikuVM does not use the standard java.lang classes but has its own versions in haikuRT and classes.jar.

See also [[Commands]].
!haikufy the program and cross-compile the resulting C Program
Calls the ~HaikuVM linker.

Usage:
haikulink [-v|"""--"""verbose] [-g|"""--"""debug] [-gr|"""--"""remotedebug] [-a|"""--"""all] 
  [-dm|"""--"""disablememcompaction] [-ea|"""--"""enableassertions] [-ec|"""--"""enablechecks] 
  ["""--"""Config <config>] ["""--"""Config:<propertyname> <value>]* [-od|"""--"""outputdebug <debug-file> ]
  -o <binary> main-class

Example:
<code bash>
haikulink -v -o HelloWorld.hex HelloWorld
</code>
Links the specified main class with any classes that it refers in the current directory and with the standard ~HaikuVM classes from haikuRT and classes.jar (from leJOS) to produce a C program. Next this C program will be cross-compiled into the binary HEX program that can be uploaded and run.

The -v or """--"""verbose flag causes a list of class names and method signatures included in the binary to be sent to the standard output. This output is extremely useful for debugging.

The -g or """--"""debug flag is not yet supported by ~HaikuVM.

The -gr or """--"""remotedebug flag is not yet supported by ~HaikuVM.

The -od or """--"""outputdebug flag is not yet supported by ~HaikuVM.

The -ec or """--"""enablechecks flag is used to enable additional run time checks. These checks are relatively expensive (and rarely generate errors) and so are off by default. The checks that this setting enables is defined in [[HaikuVM.properties]] by the property ~PanicExceptions and are usually:
*~NullPointerException
*~NoSuchMethodError
*~OutOfMemoryError
*~ClassCastException
*~VirtualMachineError
*~ArrayIndexOutOfBoundsException
*~StackOverflowError
The -ea or """--"""enableassertions flag is used to enable the checking of assert statements with the program.

The -dm or """--"""disablememcompactions flag is always set for ~HaikuVM. So memory compaction is always disabled and can not be enabled for ~HaikuVM. Normally a marture garbage collector will attempt to move large objects in memory to maximize the amount of contiguous free space, this is not implemented in the simple garbage collector of ~HaikuVM.

The linker removes methods that are not used. Specify -a or """--"""all to include all methods whether they are used or not. This should never be necessary.

The -o <binary> option is used to define the name of the output file.

The """--"""Config <config> option is an addition of ~HaikuVM to specify (overwrite) the default configuration of the [[HaikuVM.properties]].

The """--"""Config:<propertyname> <value> option is an addition of ~HaikuVM to set (overwrite) any value of the [[HaikuVM.properties]].

Use the -h or """--"""help flag to print out the options.
!upload a program
Usage: 
haikuupload ["""--"""Config:<propertyname> <value>]* <binary>

Example:
<code bash>
haikuupload HelloWorld.hex
</code>
Uploads the binary (.hex) file. 

None of the (leJOS) options are supported yet (but may be in future). Instead the upload is configurated in [[HaikuVM.properties]] and may be changed in the command line by overwriting property values with the option """--"""Config:<propertyname> <value>.
The JAVA type ''double'' type is a half precision float.
*The minimum strictly positive (subnormal) value is 2^-24 	~ 5.96 * 10^-8.
*The minimum positive normal value is 2^-14 				~ 6.10 * 10^-5.
*The maximum representable value is (2-2^-10) * 2^15 		= 65504.
The JAVA ''double'' is only a storage type. The ~HaikuVM unpacks it into a C float for calculations.
~HaikuVM supports half precision float (see [[wikipedia|http://en.wikipedia.org/wiki/Half-precision_floating-point_format]]) in case you select a 16Bit data type for JAVA type ''float''. This is only a storage type. The ~HaikuVM unpacks it into a C float for calculations.
*The minimum strictly positive (subnormal) value is 2^-24 	~ 5.96 * 10^-8.
*The minimum positive normal value is 2^-14 				~ 6.10 * 10^-5.
*The maximum representable value is (2-2^-10) * 2^15 		= 65504.
~HaikuVM, at its core, is just another JAVA VM for micros. I decided to go without building an own JAVA runtime. Instead ~HaikuVM is tailor made to use the JAVA runtime coming with [[leJOS|http://en.wikipedia.org/wiki/LeJOS]].
''NOT IMPLEMENTED'' But this is the idea:

Besides //bootclasspath// and //classpath//, well known from javac, [[haikulink]] supports a third form called //redirectmethodpath//.
For example currentTimeMillis() is defined as ''native'' in java.lang.System:
<code java>
package java.lang;
...
public class System {
...
    /**
     * Returns the current time in milliseconds.
     * This is the number of milliseconds since the AVR has been on.
     */
    public static native long currentTimeMillis();
...
}
</code>

If you don't want to implement it in plain C and you know the memory address where the millis are stored, lets say for example the address is 123, you might write a second class System including a implementation of currentTimeMillis() like this:
<code java>
package java.lang;
public class System {
    public static long currentTimeMillis() {
        return haiku.vm.MemoryAccess.getMemoryLong(123);
    }
}
</code>

Lets say the class file is 'C:\haikuVM\myCProject\redirects\java\lang\System.class' then, to use it, you have to call [[haikulink]] like this:
<code bash>
C:\haikuVM\bin\haikulink -v -redirectmethodpath C:\haikuVM\myCProject\redirects --Config arduino -o Blink.hex C:\haikuVM\examples\src\main\java\arduino\tutorial\Blink
</code>

This will ''not overwrite'' the definition of ''class'' System given in classes.jar from leJOS, but will ''overwrite only'' the implementation of the ''method'' currentTimeMillis() given in classes.jar,  hence the name of the option //redirect''method''path//.

This technique of overwriting method implementations is ''not restricted to native methods'' but will work for regular methods as well.