<meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
<html>
<!-- Generated by AceHTML Freeware http://freeware.acehtml.com -->
<!-- Creation date: 6/3/2004 -->
<head>
<meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
<title>www.mindaugas.com</title>
<meta name="description" content="">
<meta name="keywords" content="">
<meta name="author" content="mindmil@one.lt">
<meta name="generator" content="AceHTML 5 Freeware">


<style type="text/css">
<!--
A:link {font-family: Arial, Helvetica, sans-serif;  text-decoration: none; color: #006600}

A:visited {font-family: Arial, Helvetica, sans-serif;  text-decoration: none; color: #006600}

A:hover {font-family: Arial, Helvetica, sans-serif;  text-decoration: underline; color: #006600}

A:link.menu {font-family: Verdana, Arial, Helvetica, sans-serif; text-decoration: none; color: #f5f5f5}

A:visited.menu {font-family: Verdana, Arial, Helvetica, sans-serif; text-decoration: none; color: #f5f5f5}

A:link.menuhlt {font-family: Verdana, Arial, Helvetica, sans-serif; text-decoration: none; color: #f5f5b5}

A:visited.menuhlt {font-family: Verdana, Arial, Helvetica, sans-serif; text-decoration: none; color: #f5f5b5}

A:hover.menu {font-family: Verdana, Arial, Helvetica, sans-serif; text-decoration:underline; color: #f5f5f5}

.menu {font-family: Verdana, Arial, Helvetica, sans-serif; color: #f5f5f5}

.menuhlt {font-family: Verdana, Arial, Helvetica, sans-serif; color: #f5f5d5}

td {background:   transparent; color: navy; font-family: Arial, Helvetica, sans-serif; font-size: 9pt}

body {background-color: #dcdcdc; font-size: 9pt}

.mainmenu {background-color: #191970; color: #f5f5f5; font-size: 10pt; width: 120px}

.rightpanel {background-color: #191970; color: #f5f5f5; font-size: 10pt; width: 120px}

.mainmenuline {color: #c0c0c0;noshade}

.field_name2 {background-color: #191970; color: #f5f5f5; }
.field_name {background-color: #303080; color: #f5f5f5; }
.field_value {background-color: #dcdcdc; color: #000080; }

.submenu {background-color: #4169E1; color: #f5f5f5; font-size: 9pt}

.submenu2 {background-color: #EAEAF3; color: #000080; font-size: 9pt}

.submenu2_lll {background-color: #fAfAF3; color: #bF4500; font-size: 9pt}

.submenu2_l {background-color: #fff6E0; color: #000080; font-size: 9pt}
.submenu2_l_2 {background-color: #fAfAF3; color: #000080; font-size: 9pt}

.submenu2_anouncement2 {background-color: #ddFFdd; color: #000080; font-size: 9pt}

.submenu2_anouncement {background-color: #FFfbcc; color: #d02000; font-size: 9pt}
.submenu2_anouncement_big {background-color: #FFfbcc; color: #d02000; font-size: 14pt}

.submenu2_anouncement4 {background-color: #FFfbcc; color: #800000; font-size: 9pt}

.submenu2_anouncement3 {background-color: #FFfbcc; color: #000080; font-size: 9pt}

.submenu2_lt {background-color: #fAfAF3; color: #f5f5f5; font-size: 9pt}

.submenu2_body2 {background-color: #FFFFeb; color: ##800000; font-size: 9pt}

.submenu2_body {background-color: #FFFff7; font-size: 9pt}
.submenu2_body3 {background-color: #dcdcdc; font-size: 9pt}

.submenuitem {background-color: #4169E1; color: #f5f5f5; width: 70px}

.titlebar {background: #FFA500; color: #800000}

.footerbar {background: #FFA500; color: #800000}

h1 {font-size: 16pt}

h2 {font-size: 14pt}

h3 {font-size: 12pt}

h4 {font-size: 10pt}

h5 {font-size: 8pt}

h6 {font-size: 6pt}

.textstyle {font: bold 12px Verdana;  line-height: 1.5;}

.rgdsmailstyle {font: italic bold 12px Verdana;  line-height: 1.5;}

.formstyle {background-color: #E1E1E1;}

/* End of style section. Generated by AceHTML at 2/7/2005 11:43:21 PM */
-->
</style>

<meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">


<script type="text/javascript">
var contacts=new Array()
contacts[0]=["Mindaugas Milasauskas", "mindaug[eta]mindaugas[taskas]com"]
contacts[1]=["mindaug[eta]mindaugas[taskas]com", "mindaug[eta]mindaugas[taskas]com"]
contacts[2]=["sales[eta]mindaugas[taskas]com", "sales[eta]mindaugas[taskas]com[klaustukas]subject[lygu]MJoy16-C1 ordering"]
var dropmenucaption="CONTACT US FORM "

function displaycontact(emailarray, cssclass, displaymethod, extrainfo)
{
	if (displaymethod=="text")
	{
		document.write('<span class="' + cssclass + '">\n')
		if (typeof emailarray[0]=="object")
		{ 
			for (i=0; i<emailarray.length; i++)
			{
				var seperator=(i<emailarray.length-1)? extrainfo : ""
				if (emailarray[i][0] == "")
					document.write('<a href="mailto:' + modifyemail(emailarray[i][1])+ '">'+ emailarray[i][1] + '</a>' + seperator)
				else
					document.write('<a href="mailto:' + modifyemail(emailarray[i][1])+ '">'+ emailarray[i][0] + '</a>' + seperator)
					
			}
		}
		else //else if it is a single array element
		if (emailarray[0] == "")
			document.write('<a href="mailto:' + modifyemail(emailarray[1])+ '">'+ modifyemail(emailarray[1]) + '</a>')
		else
			document.write('<a href="mailto:' + modifyemail(emailarray[1])+ '">'+ modifyemail(emailarray[0]) + '</a>')
		document.write('</span>')
	}
	else if (displaymethod=="form")
	{
		document.write('<form>\n')
		document.write('<select size="' + extrainfo + '" onChange="jumptooption(this)" class="' + cssclass + '">\n')
		document.write('<option value="caption">' + dropmenucaption + '</option>\n')
		for (i=0; i<emailarray.length; i++)
			document.write('<option value="mailto:' + modifyemail(emailarray[i][1]) +'">' + emailarray[i][0] + ' </option>\n')
		document.write('</select></form>\n')
	}
}

function modifyemail(emailitem){
var modified=emailitem.replace(/\[eta]/gi, "@")
modified=modified.replace(/\[taskas]/gi, ".")
modified=modified.replace(/\[klaustukas]/gi, "?")
modified=modified.replace(/\[lygu]/gi, "=")
return modified
}

function jumptooption(themenu){
if (themenu.options[themenu.selectedIndex].value !="caption")
location=themenu.options[themenu.selectedIndex].value
}
</script>
		
		
</head>
<body>  <!-- bgcolor="#ffffcc" text="#000000" link="#0000ff" vlink="#800080" alink="#ff0000"> -->

<table width="800" align="center" border="0" cellpadding="0" cellspacing="0" bordercolor="#000000" summary="">
	<tr>
		<td height="24" class=titlebar align="center">
		<span style="font: normal; font-family:     sans-serif; font-size: 18pt; font-weight: bold">Mindaugas' Home</span>
		</td>
	</tr>
	<tr>
		<td>
	<table border="0" height="600" cellpadding="0" cellspacing="0" bordercolor="#000000" summary="" >
	<tr>
		<td width="120" align="left" valign="top" class=mainmenu> 
			 <table  border="0" cellpadding="4" cellspacing="0" bordercolor="#000000" summary="" >
				<tr>
					<td class=mainmenu > 
					
												<div >
						<b><a href="../../default.htm" title="Home" class=menu>Home</a></b>						 </div>
						 <hr class=mainmenuline>
														<div >
						<b><a href="../default.htm" title="Projects" class=menu>Projects</a></b><br>&nbsp;&nbsp;<a href="default.htm" title="MJoy" class=menu>MJoy</a><br>&nbsp;&nbsp;&nbsp;&nbsp;<a href="Article.php" title="Article" class=menuhlt>Article</a><br>&nbsp;&nbsp;&nbsp;&nbsp;<a href="Versions.php" title="Versions" class=menu>Versions</a><br>&nbsp;&nbsp;&nbsp;&nbsp;<a href="Programmer.php" title="Programmer" class=menu>Programmer</a><br>&nbsp;&nbsp;&nbsp;&nbsp;<a href="FAQ.php" title="FAQ" class=menu>FAQ</a><br>&nbsp;&nbsp;&nbsp;&nbsp;<a href="Links.php" title="Links" class=menu>Links</a><br>&nbsp;&nbsp;<a href="../MJoy16/default.htm" title="MJoy16" class=menu>MJoy16</a>						 </div>
						 <hr class=mainmenuline>
														<div >
						<b><a href="../../products/default.htm" title="Products" class=menu>Products</a></b>						 </div>
						 <hr class=mainmenuline>
														<div >
						<b><a href="../../software/default.htm" title="Software" class=menu>Software</a></b>						 </div>
						 <hr class=mainmenuline>
														<div >
						<b><a href="../../about.php" title="About" class=menu>About</a></b>						 </div>
						 <hr class=mainmenuline>
																				 
					</td>
				</tr>
		 	</table>
		 </td>
		<td width="680" align="justify" valign="top" bgcolor="#FFFFCC"  class="submenu2_body" >
	



		<meta http-equiv="Content-Type" content="text/html; charset=windows-1257">
<table   width="100%" border="0" cellpadding="4" cellspacing="0" bordercolor="#000000" summary="">
	<tr>
		<td class="submenu">
			<h2>MJoy</h2>
			<h4>USB Joystick Controller on AVR ATMega8 microcontroller
			</h4>
			<h5>By Mindaugas Milasauskas <!-- a.k.a. virtual pilot callsign MeanDog --><br>
			Based on design of Igor Cesko “USB to RS232” controller</h5>
		</td>
	</tr>
	<tr>
		<td align="justify"><br>

<b>Note: Article schematic diagram was updated to include zener diodes and resistors which are necessary to for proper operation with all types
of USB host controllers. Schematic without these modifications may not work with all USB host controller types. <i>2005-02-08</i></b>
		
		<br><h4>Introduction
</h4>
<div style="text-align:justify;">I have started developing this joystick controller inspired by the 
need of simple DIY joystick which could overcome limitations of 
gameport and deliver greater accuracy and flexibility in the possible designs. 
I realized the need for such device because I like to play IL2 Sturmovik game. 
This game has obvious demand for high quality joystick unless you are happy being dead meat. 
Most mass market joysticks have lots of flaws. And there are a lot of guys who 
make joysticks of their own design. Many of these designs are much better than mass production ones. 
For most of these designs the controller is needed. 
Using gameport would ruin all the efforts of high precision mechanics. 
There are many of these discussions on IL2 game forums. 
The obvious demand was for USB joystick controller so I pursued in this direction. And here it is…
<br><br><br>

<h4>Investigation
</h4>
The best way looked to find a suitable USB enabled controller and implement application on it. 
But after looking for various possibilities it was obvious that it is not easy to get such a 
device for reasonable price in reasonable time for DIY amateur. The other possibility was to 
take some generic microcontroller and implement USB protocol on it as well as application 
level procedures. Looking across the Internet I found Igor Cesko page 
<a href="../../../cesko.euro-science.net/default.htm" title="Igor's page">http://cesko.euro-science.net/</a>.<br> 
Igor has made good investigation and big work in implementing USB protocol on microcontroller. 
So I decided to take his design as a basis and implement everything what is needed for joystick on top. 
I chose ATMega8 as it was cheap and easy to get component for the design. Cheers, Igor! :)<br>
Next it was time for investigating HID firmware implementation. After that it was also needed 
to dig a bit deeper in USB specifications as implementation of USB interrupts was not included in Igor’s device. 
After intensive evening work for couple of weeks I managed to get this controller working.<br>
<br>
<br>
<h4>Hardware</h4>

Hardware component basis is very minimal for this controller so most of DIY electronics hobbyists 
even with limited experience could repeat it and build the super-joystick by themselves. 
The main brain is ATMega8 microcontroller in DIP package with 12MHz quartz resonator. 
Few resistors and capacitors are everything what is needed to get it working.
Schematic diagram is shown below:<br>
<a href="Schematic.png"><img src="Schematic_thumb.gif" border="0" alt="MJoy schematic diagram"><br>
Click to enlarge</a>
<br><br>
The connection of controller to joystick sensors and buttons is very simple. In this schematics 
it is shown with potentiometers but it may be also some other axis position sensors – magnetic, 
optic and other. I am also working on connecting this controller to my UR Gear modified helmet. 
I will also show some alternative hardware+software joystick configurations. ADC inputs in this 
design take the voltages from 0 to 5 volts as full range. But smaller range is possible. 
Hat switch uses buttons PD7-PD3, PD7-PD4, PD7-PD5, PD7-PD6. Capacitors used here are filtering ones and 
usually have value of 0.1 µF but any similar ones should do as well.<br>
The controller has no PCB design ready and you will have to create your own. Or maybe I’ll do it 
at some later time when I have some spare time which I never have. :) 
My piece is made on generic drilled PCB with several wires connecting the components:<br>

<a href="PCB_top.jpg"><img src="PCB_top_thumb.jpg" border="0"  alt="Top"></a>
<a href="PCB_conn.jpg"><img src="PCB_conn_thumb.jpg" border="0" alt="Connectors"></a>
<a href="PCB_bottom.jpg"><img src="PCB_bottom_thumb.jpg" border="0"  alt="Bottom"></a><br>
Click images to enlarge
<br>
<br>
One connector is for USB another is for ISP programming adapter which is shown below. I know it doesn’t look very nice but it does it's job. 
I would be very thankful to anyone who could build the PCB and would send one piece to me. :) (It's a joke)
<br>
<br>
<br>
<h4>Software</h4>

All the needed software is in microcontroller. No additional Windows drivers needed. Thanks to HID class. 
The development and assembly was done using AVR Studio 4. 
Most of basic USB protocol handling parts are left from Igor’s firmware. 
Additional routines were added: HID specific descriptor handling, Interrupt In handling, 
joystick data acquiring from ADCs and buttons and stuffing this data to 8 byte long reports. 
Some unneeded routines were removed.<br>
The software version published here is for one of possible joystick configuration. 
This is for 6 axis, 8 position hat switch, 24 buttons joystick:<br>
<ul>
  <li>2 x 10 bit ADC inputs for X, Y axis<br></li>
  <li>1 x 8 bit ADC input for Throttle axis<br></li>
  <li>1 x 8 bit ADC input for Rudder axis<br></li>
  <li>1 x 8 bit ADC input for Slider axis<br></li>
  <li>1 x 8 bit ADC input for Dial axis<br></li>
  <li>1 x 8 position Hat switch (Hat uses 4 button switches)<br></li>
  <li>24 buttons<br></li>
</ul>

It uses almost all data input resources available on ATMega8 DIP packaged chip. If you have ATMega16 
or greater you can have even more axes and buttons. The AVR Studio 4 project file with source 
code and assembled binary for this controller version is here:<br>

<a href="MJoy_v1.1.zip" title="MJoy project files"><b><font color="#006600">MJoy_v1.1.zip</font></b></a><br><br>

There may be huge amount of other possible configurations. If you need custom configuration you 
could build your own. In next section I’ll describe how. <br><br>
<br>

<h4>Installation</h4>

Installation is accomplished by simply plugging in the device into the USB port of the computer. 
The OS should find the device and install it as a joystick. You should find your USB joystick 
among gaming devices. It should appear as “MJoy”:<br>
<a href="Game_controllers.gif"><img src="Game_controllers_thumb.gif" border="0" alt="Game Controllers"></a> 
<a href="MJoy_properties.gif"><img src="MJoy_properties_thumb.gif" border="0" alt="MJoy properties"></a><br>
Click images to enlarge<br>
It was tested on Windows 2000 and Windows XP computers.
This controller does not have automatic calibration function. But it may be implemented in future. 
For now you will need to calibrate this joystick using standard Windows joystick calibration procedure.


<h4>What is needed to build custom joystick configuration
</h4>
I won’t dig deep into Igor’s implementation as you can read his documentation and investigate by your own. 
I will try to describe my part and hope it will help you to build your own joystick configurations. 
For that you will have to get yourself a bit familiar with AVR microcontroller assembly instructions. 
Programming in higher level languages is not suitable as the Igor’s code contains some time-tight routines. 
The possible configurations limit is 64 bits for one report which you should use to stuff all the 
data from your custom controller. It may be 64 buttons console for flight controls either 8 x 8 bit 
axes analog controls for propeller pitch, flaps and trimmers or anything in between. You choose.<br> 
Another possibility is to use several reports with different IDs to send virtually as much information as you wish. 
The drawback is that the lowest report query interval limit is 10ms. In case you have several 
reports sent back in cyclic manner the overall device poll rate would decrease. In the implementation 
presented here there are 2 reports which are sent back cyclically. As a result this joystick poll period of 20ms.

<h4>HID USB device Enumeration</h4>

All USB devices start operating with Enumeration. After getting enumeration information host 
operating system knows which drivers to load to be able to use the device. For HID devices 
Windows have drivers built-in and no special drivers needed. All that is needed is that device 
return the descriptors which conform to HID firmware specifications. <br>
In addition to minimal generic USB device descriptors additional descriptors are needed for 
minimal HID device: HIDDescriptor and ReportDescriptor. All these descriptors are at the end of source file.<br>

ReportDescriptor is the main structure telling what kind of joystick it is and what are its inputs. 
If you want to build your own configuration you will have to familiarize yourself with this 
structure and understand it. There are specifications and some examples from which you should be 
able to learn how to get what you want. Please familiarize yourself with HID documentation part 
about Report descriptor to be able to create meaningful structure. The HID tool has example files 
of some commonly used descriptors to help you out with this.<br>
In this implementation it has defined that it uses 2 reports with IDs 1 and 2. The size of the 
report data returned back in each of them is defined by JoystickReport1Size and JoystickReport2Size values. 
These values state the size of each report. <br>
In this case ReportID1 has 8 bytes. First byte carries report ID. The next 7 bytes carry information 
about axes and Hatswitch. ReportID2 has 4 – 1 for ID + 3 for 24 buttons. These values are used in 
ProcJoystickRequest routine which is discussed later.<br>
After editing ReportDescriptor you should update the ReportDescriptorSize value 
Equal to the size of ReportDescriptor structure in bytes. So pay attention to it when you edit 
ReportDescriptor.  Making an error would result your joystick not to appear in joysticks list. 
HID test tool is also useful for this calculating descriptor size. It can tell you what is the 
size of this descriptor when you add all the fields in it. But at the end I got used to recalculate 
it manually on the fly.<br>

There is also some important field in EndpointDescriptor – polling interval. You can define your 
own value in range from 10 to 255. It will define the polling frequency. With default 10 milliseconds 
value controller is polled 100 times in a second. But also remember how many reports you have to 
calculate your joystick polling period.<br>

If you are building your custom configuration also update the fields VendorUSBID, DeviceUSBID and 
DeviceVersion. You may also want to change the name of the device string but please leave the 
copyright credits in VendorStringDescriptor. This is for me and for Igor.<br>


<h4>Joystick Data Acquiry and Report Formatting
</h4> 
All joystick input data processing is done in ProcJoystickRequest routine. You would also have to 
modify it to correspond to ReportDescriptor if you wand to build custom configuration joystick. 
This routine is called in spare time between the data polls. The complexity of it might affect 
the poll time. If it is too complex you might need to increase the polling period as described above. 
Also it is worth to note that some ADC and button inputs preparation instructions are in reset routine. 
So if you are changing some pins behavior, look in there. One important parameter there is ADC prescaler 
division factor. It defines how fast ADC conversion goes. In this design it is 64 which gives 
187khz clock for ADC.  You can try to 
make prescaler value smaller to make A-D conversion go faster. But this might decrease the accuracy of ADC.
Recommended ATMega guideline is up to 200kHz for accurate results.<br>
In presented version the software reads values from all ADC inputs and reads buttons matrix using 
all other spare pins of ATMega8.
Two branches process Report1 and Report2 which are defined in ReportDescriptor. They are selected 
in cyclic order.
There are procedures which read 10 or 8 bit ADC inputs. The input parameter for them is carried 
in temp0 which is the number of Port C pin to read. Other procedure reads a row of buttons formed 
using port D and port B pins. All the results are written into the JoystickBuffer using the structure 
defined in ReportDescriptor. <br>
<br>
<br>
<h4>Programming the controller</h4>

The controller was programmed using very simple programmer. I like using simple tools for simple tasks :).<br><br>

<h4>Programmer Hardware</h4>

Hardware is very simple: <br>

<a href="avrisp.gif"><img src="avrisp_thumb.gif" border="0" alt="AVR programmer hardware"></a>
<a href="IMG_0466.jpg"><img src="IMG_0466_thumb.jpg" border="0" alt="Programmer Top"></a>
<a href="IMG_0467.jpg"><img src="IMG_0467_thumb.jpg" border="0"  alt="Programmer Bottom"></a><br>
Click images to enlarge<br>
<br>
It has a bit dirty design but it works for me and I don’t think something much more is needed. <br>
<br>

<h4>Programmer Software</h4>

I use PonyProg to program the controller. You can find the latest version on this website:<br>
<a href="../../../www.lancos.com/prog.html" title="PonyProg">http://www.lancos.com/prog.html</a>
<br>

<h4>Programming Procedure</h4>

<ol>
	<li>Connect the controller to USB port on your computer. This is needed to provide +5V power supply. Connect the programmer to LPT1 port on your computer. Connect the programmer to your controller (I use simple LAN patch cord).</li>
	<li>Start PonyProg program. On first start it proposes to make calibration to adjust itself to your PC speed. Let it do it. Alternatively use Setup->Calibration from menu.</li>
	<li>Make setup of programmer interface using Setup->Interface Setup... Make settings according to picture below.<br>
		<a href="Device_setup.gif"><img src="Device_setup_thumb.gif" border="0"  alt="Interface Setup"><br>
		Click image to enlarge</a></li>
	<li>Select ATMega8 chip as the device you want to programm from menu Device->ATMega8 as shown on the picture.<br>
		<a href="Chip_setup.gif"><img src="Chip_setup_thumb.gif" border="0" alt="Chip Select"><br>
		Click image to enlarge</a></li>
	<li>Open mjoy.hex file using menu File->Open Program (FLASH) File...</li>
	<li>Program the chip using Command->Write Program (FLASH) menu.</li>
	<li>Program the chip configuration bits using Command->Security and Configuration bits... Set flags as shown below and hit Write to program them.<br>
		<a href="Configuration_bits.gif"><img src="Configuration_bits_thumb.gif" border="0" alt="Configuration bits"><br>
		Click image to enlarge</a></li>
	<li>Close PonyProg, disconnect the programmer and replug your new megajoystick to USB port.</li>
</ol>

<br><br><br>
<h4>Licence and Copyrights</h4>

All information in this published document and all source codes is free for non commercial use.<br> 
All presented programs and source code are under GPL licence (for non commercial use).<br>
<br>
Copyright © 
<script type="text/javascript">
		displaycontact(contacts[0], "", "text", " | ")
</script> 
2004, Lithuania, www.mindaugas.com 
<br>
Copyright © Ing. Igor Cesko 2003, Slovakia, http://cesko.euro-science.net/ , cesko@internet.sk <br>
<br>
<br><br>
<h4>References:</h4>
<ol>
	<li><a href="http://www.fly-by-night.de//cesko.euro-science.net/default.htm" title="Igor Cesko Homepage">Igor Cesko “USB to RS232” controller</a></li>
	<li><a href="http://www.fly-by-night.de//www.usb.org/developers/docs/default.htm" title="USB Documents">USB Documents</a></li>
	<li><a href="http://www.fly-by-night.de//www.usb.org/developers/docs/usbspec.zip" title="USB 1.1 Specifications">USB Specifications</a></li>
	<li><a href="http://www.fly-by-night.de//www.usb.org/developers/hidpage/default.htm" title="HID Web page">HID Web page</a></li>
	<li><a href="http://www.fly-by-night.de//www.usb.org/developers/devclass_docs/HID1_11.pdf" title="HID 1.11 Specifications">HID Specifications</a><br></li>
	<li><a href="http://www.fly-by-night.de//www.usb.org/developers/hidpage/dt2_4.zip" title="HID Descriptor Tool">HID Descriptor Tool</a> - good for creating your own Report Descriptors<br> </li>
	<li><a href="http://www.fly-by-night.de//benoit.papillault.free.fr/usbsnoop/default.htm" title="USB Sniffer v1.8">USB Sniffer v1.8</a> - good for troubleshooting<br> </li>
	<li><a href="http://www.fly-by-night.de//www.atmel.com/products/AVR/default.htm" title="Atmel AVR microcontrollers">Atmel AVR microcontrollers</a> - <br> </li>
	<li><a href="http://www.fly-by-night.de//www.atmel.com/dyn/products/tools_card.asp@tool_id=2725" title="AVR Studio 4">AVR Studio 4</a> - good tool for programming and debugging AVR microcntrollers<br> </li>
	<li><a href="http://www.fly-by-night.de//www.qsl.net/ba1fb/default.htm" title="Simple AVR ISP programmer">Simple AVR ISP programmer hardware</a><br> </li>
	<li><a href="http://www.fly-by-night.de//www.lancos.com/prog.html" title="PonyProg">PonyProg</a> - good AVR programming software<br> </li>
	<li><a href="http://www.fly-by-night.de/./vkb.sukhoi.ru/elektron/mjoy.htm" title="MJoy in vkb.sukhoi.ru website">MJoy in vkb.sukhoi.ru</a> - this article in Russian<br> </li>
</ol>
<br><br><br>
Enjoy and please send your comments to me.
<br>
Regards,<br>
<script type="text/javascript">
		displaycontact(contacts[0], "rgdsmailstyle", "text", " | ")
</script>
<br><br><br>
<h5>Last update: 2005-02-08</h5>
</div></td>
	</tr>
</table>
		

</td>
</tr>
</table>
		</td>
	</tr>
	<tr>
		<td height="12" class=footerbar align="center">
		</td>
	</tr>

</table>


</body>
</html>