<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="de">
	<id>https://www.mikrocontroller.net/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=213.179.131.90</id>
	<title>Mikrocontroller.net - Benutzerbeiträge [de]</title>
	<link rel="self" type="application/atom+xml" href="https://www.mikrocontroller.net/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=213.179.131.90"/>
	<link rel="alternate" type="text/html" href="https://www.mikrocontroller.net/articles/Spezial:Beitr%C3%A4ge/213.179.131.90"/>
	<updated>2026-04-11T03:16:15Z</updated>
	<subtitle>Benutzerbeiträge</subtitle>
	<generator>MediaWiki 1.39.7</generator>
	<entry>
		<id>https://www.mikrocontroller.net/index.php?title=Bluetooth_Maschinensteuerung_mit_XMC2GO_und_Android-App&amp;diff=92248</id>
		<title>Bluetooth Maschinensteuerung mit XMC2GO und Android-App</title>
		<link rel="alternate" type="text/html" href="https://www.mikrocontroller.net/index.php?title=Bluetooth_Maschinensteuerung_mit_XMC2GO_und_Android-App&amp;diff=92248"/>
		<updated>2016-03-07T12:32:04Z</updated>

		<summary type="html">&lt;p&gt;213.179.131.90: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&#039;&#039;von Vision&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
[[Datei:XMC2GO Board.JPG|gerahmt|XMC2GO mit XMC1100]]&lt;br /&gt;
== Einleitung ==&lt;br /&gt;
&lt;br /&gt;
Ziel dieses Projekts war es, eine ältere Industriemaschine (einen Stapelschneider des Typs Ideal 9221-95) komfortabel über ein Tablet oder Smartphone bedienbar zu machen. Dabei sollte die schon vorhandene Elektronik (Motorsteuerung und Bedieneinheit) erhalten bleiben, um die Maschine jederzeit wieder vollständig zurück rüsten zu können. Da ich gerne ein Projekt mit dem XMC2GO umsetzen wollte, war dieses Vorhaben ideal für den Einstig mit der neuen Controllerfamilie.&lt;br /&gt;
&lt;br /&gt;
== Hardware ==&lt;br /&gt;
folgende Hardware sollte (weil vorhanden) für die Umsetzung des Projekts verwendet werden:&lt;br /&gt;
&lt;br /&gt;
* [http://www.infineon.com/cms/de/product/evaluation-boards/KIT_XMC_2GO_XMC1100_V1/productType.html?productType=db3a304443537c4e01436ccecb5d154f Entwicklungsboard XMC2GO]&lt;br /&gt;
* [http://www.intersil.com/en/products/data-converters/digital-potentiometers--dcps-/dcps/X9C102.html Digital Potentiometer X9C102SZ]&lt;br /&gt;
* [http://www.rayson.com/rayson/en/index.php?pros=product&amp;amp;pros=product&amp;amp;b_cat_id=A01&amp;amp;m_cat_id=A0101&amp;amp;s_cat_id=A010102&amp;amp;prod_id=P0018&amp;amp;level=3 Bluetooth Modul BTM222]&lt;br /&gt;
* Stapelschneider des Typs IDEAL 9221-95&lt;br /&gt;
* Android Handy / Tablet&lt;br /&gt;
&lt;br /&gt;
== Software ==&lt;br /&gt;
für die Umsetzung dieses Projektes benötigte ich folgende Software&lt;br /&gt;
&lt;br /&gt;
* Keil µVision5 &lt;br /&gt;
* HTerm 0.8.1 beta&lt;br /&gt;
* MIT App Inventor 2&lt;br /&gt;
&lt;br /&gt;
== Projektbeschreibung ==&lt;br /&gt;
[[Datei:IDEAL9221-95.jpg|miniatur|Stapelschneider IDEAL 9221-95 ]]&lt;br /&gt;
Wie oben schon erwähnt, geht es bei diesem Projekt darum, den Bedienkomfort einer Maschine zum Schneiden von Papierstapeln zu erhöhen. Von Werk aus ist der Stapelschneider mit einem elektrisch verstellbaren Tiefenanschlag ausgerüstet. Dabei sorgt ein Gleichstrommotor für die Positionierung. Die Positionsbestimmung erfolgt über eine Encoderscheibe auf der Welle des Motors, die von einem Lichtschranken-Pärchen abgetastet wird. Gesteuert wird das Gerät über ein Potentiometer an der Front. Die aktuelle Position kann auf einer vierstelligen Siebensegmentanzeige abgelesen werden.&lt;br /&gt;
Die Einstellung über das Potentiometer ist jedoch alles andere als komfortabel, da man damit auch schnell mal über das eigentliche Ziel heraus schießt. Es wäre viel praktischer, die gewünschte Position des Tiefenanschlages einzugeben und die Maschine den Rest machen zu lassen.&lt;br /&gt;
&lt;br /&gt;
Hier startet nun das eigenliche Projekt. Über ein Mikrocontroller und ein Digital-Potentiometer sollte man die Maschine doch steuern können. Wenn noch ein Bluetooth-Modul dazu kommt, dann sogar mit einem Smartphone oder einem Tablet. Zum auslesen der Position bieten sich zwei Möglichkeiten. Zum einen das &#039;Anzapfen&#039; der Siebensegmentanzeige, zum anderen die Verwertung der Signale der Lichtschranke. Da der &#039;Eingriff&#039; in die vorhandene Technik möglichst nicht-invasiv sein sollte und die Lichtschranke (sowie Poti und Endschalter) über Stecker an die eigentliche Steuerplatine angeschlossen sind, habe ich mich für die Auswertung der Lichtschranken entschlossen. &lt;br /&gt;
&lt;br /&gt;
Was musste also die Firmware meiner Steuerung können?&lt;br /&gt;
&lt;br /&gt;
1. Externe Interrupts erfassen (Signale der Lichtschranke und des Endschalters)&amp;lt;br&amp;gt;&lt;br /&gt;
2. Analog-Digital-Conversion (man soll das Gerät ja auch weiterhin über den vorhandenen Poti steuern können)&amp;lt;br&amp;gt;&lt;br /&gt;
3. Three-Wire Serial Interface für die Steuerung des Digitalpotis&amp;lt;br&amp;gt;&lt;br /&gt;
4. UART über Bluetooth&amp;lt;br&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Klingt erstmal nach überschaubarem Aufwand. Aber es ist wie überall im Leben - der Teufel steckt im Detail.&lt;br /&gt;
&lt;br /&gt;
Erstellt habe ich die Firmware - wie oben schon aufgeführt - mit der µVision5 IDE von Keil. &lt;br /&gt;
Für die Controller der Infineon XMC1000-Reihe gibt es eine kostenlose Version, mit der man Programme bis 128k kompilieren und debuggen kann [http://www2.keil.com/infineon/mdk/ [1&amp;lt;nowiki&amp;gt;]&amp;lt;/nowiki&amp;gt;].&lt;br /&gt;
Nach einer kurzen kostenlosen Registrierung kann man den Installer direkt runterladen und dank der ausführlichen Anleitung fällt auch das Einrichten der IDE nicht weiter schwer.&lt;br /&gt;
&lt;br /&gt;
Nachdem also die IDE installiert war, ging es erst einmal darum, die externen Interrupts zu erfassen. Und genau hier fingen die Schwierigkeiten an. Es sind im Internet noch relativ wenig Informationen über die XMC-Familie zu finden und das, was man findet, stützt sich auf die DAVE3 Entwicklungsumgebung von Infineon mit den diversen DAVE-Apps. Da es sich dabei aber - wie ich es verstanden habe - um dynamisch erzeugten Code handelt, hat es mir bei meiner Frage, wie man die Interrupts in einer anderen IDE ohne DAVE-Apps einrichten und auswerten kann, nicht wirklich weiter geholfen. Hilfe habe ich letztendlich im Forum &#039;infineonforums.com&#039; [http://www.infineonforums.com/ [2&amp;lt;nowiki&amp;gt;]&amp;lt;/nowiki&amp;gt;] erhalten. Dort wurde mir der Link zu einem Code-Example [http://www.infineon.com/dgdl/Simple_XMC1200_ERU.exe?folderId=db3a30433580b3710135a47f3eb76c98&amp;amp;fileId=db3a30433efacd9a013f0efc19ad42d7&amp;amp;sd=t [3&amp;lt;nowiki&amp;gt;]&amp;lt;/nowiki&amp;gt;] gegeben, welches zwar auch mit der DAVE-IDE erstellt wurde, bei die Initialisierung der Interrupts jedoch manuell ohne App umgesetzt wurde.&lt;br /&gt;
Damit war es mir nun auch möglich, die Interrupts auf steigende und fallende Flanken an der Lichtschanke, sowie nur der steigenden Flanke des Endschalters zu initialisieren und auf diese zu Reagieren.&lt;br /&gt;
&lt;br /&gt;
[[Datei:BelegungStecker.jpg|miniatur|Steckerbelegung an der Steuerplatine des Stapelschneiders]]&lt;br /&gt;
Die Signalquellen sind, wie oben erwähnt, durch Stecker mit der Steuerungsplatine verbunden. Diese Verbindungen nutze ich, um die Signale abzugreifen und die Signale meines Digital-Potentiometers einzuspeisen.&lt;br /&gt;
&lt;br /&gt;
[[Datei:Rechteck.jpg|miniatur|Um eine halbe Phase verschobenes Rechtecksignal]]&lt;br /&gt;
Die ISR (Interrupt Service Routine), die die Positionsänderungen erfassen sollte, gestaltete sich nun recht einfach. Das Lichtschranken-Pärchen liefert logischerweise für jede Lichtschranke ein Rechtecksignal, solange sich der Motor dreht. Die Signale der beiden Lichtschranken sind eine halbe Phase zueinander verschoben. Einen Interrupt habe ich nur für die eine Lichtschranke initialisiert. Dieser löst bei jeder steigenden und fallenden Flanke, also immer wenn sich der Zustand von High auf Low oder von Low auf High ändert, aus. In der ISR brauche ich dann nur noch zu erfassen, welcher Pegel an den beiden Eingängen, an denen die Lichtschranken angeschlossen sind, anliegt und diese beiden Pegel zu vergleichen. Wenn beide Pegel gleich sind (egal ob High oder Low), dreht der Motor in die eine Richtung und ich zähle eine vorher initialisierte Zählervariable um einen Zähler hoch. Sind die beiden Werte unterschiedlich, dreht der Motor in die andere Richtung und ich zähle meine Variable herrunter. Somit habe ich schon einmal eine relative Positionsbestimmung. &lt;br /&gt;
Allerdings kann ich nicht wissen, an welcher Position die Maschine startet (das weiß die Maschine nicht einmal selbst).&lt;br /&gt;
&lt;br /&gt;
Hier kommt nun der hintere Endschalter ins Spiel. Da die Maschine über keinen nichtflüchtigen Positionsspeicher (wie beispielsweise ein EEPROM) ferfügt, &#039;vergisst&#039; sie bei jedem Ausschalten, an welcher Position sich der Tiefenanschlag befindet. Wenn die Maschine eingeschaltet wird, ist somit eine sogenannte Referenzfahrt nötig. Hierzu muss man im Originalzustand des Stapelschneiders den Poti einmal kurz auf &#039;zurück&#039; stellen. Eine eingebaute Feder bringt den Poti wieder in die neutrale Stellung und der Tiefenanschlag fährt zurück, bis dieser den Endschalter erreicht hat. Nun weiß die Maschine, dass sich der Schlitten bei genau 520mm hinter dem Messer befindet. In meiner Steuerung habe ich dem Eingang, auf den der Endschaltergelegt ist, auch einen Interrupt spendiert. Sobalt der Endschalter auslöst, setze ich meine oben schon erwähnte Zählerwariable auf den maximalen Wert von 46800. Diese Zahl setzt sich folgendermaßen zusammen: Ich benötige eine genauigkeit von einem Zehntel Millimeter. Der maximal erreichbare Wert bis der Endschalter ausgelöst wird, beträgt 520mm. Das sind 5200 1/10mm. Bei jedem 1/10mm, den sich der Schlitten bewegt, wird neun mal ein Interrupt ausgelöst. Somit ist der Maximalwert meiner Variable 5200x9=46800.&lt;br /&gt;
Damit diese Position nun beim Starten erfasst wird, wird das digitalpotentiometer beim starten der Firmware für eine kurze Zeitspanne (300ms) auf &#039;zurück&#039; gestellt und anschließend wieder die Neutralposition eingestellt, ganz so, als würde man die Maschine direkt bedienen.&lt;br /&gt;
&lt;br /&gt;
[[Datei:AnalogPoti.jpg|miniatur|Analogpoti zur Steuerung des Tiefensnschlags]]&lt;br /&gt;
Um den Stapelschneider weiterhin direkt mit dem analogen Potentiometer an der Maschine zu bedienen, wird laufend der Wert des Potentiometers mittels ADC eingelesen. Wenn dieser von dem beim Start gespeicherten Wert (inkl. einer kleinen Hysterese von +-10) abweicht, wird automatisch das digitale Potentiometer diesem Wert angepasst und eine eventuell noch nicht abgearbeitete Positionsänderung gelöscht.&lt;br /&gt;
&lt;br /&gt;
Damit sind wir auch schon beim nächsten Punkt. Positionsänderungen (bzw. gewünschte absolute Positionen) werden über UART empfangen und abgearbeitet. Dabei musste darauf geachtet werden dass die Positionen immer nur aus einer Richtung angefahren werden dürfen (von hinten), da sich sonst das Umkehrspiel des Schlittens bemerkbar machen würde. Sollte die gewünschte neue Position also hinter der aktuellen Position legen. Muss der Schlitten noch ein stück weiter zurück fahren, um die gewünschte Position dann von hinten anfahren zu können.&lt;br /&gt;
&lt;br /&gt;
Die Positionsänderungen wurden, wie oben erwähnt, ursprünglich mit einem Analogen 1k-Ohm Potentiometer durchgeführt. In Neutralstellung war das Poti auf etwa 800 Ohm eingestellt. Um den Tiefenanschlag nach hinten zu bewegen, musste man das Potentiometer richtung 1000 Ohm verdrehen. Wenn man losgelassen hat, ist es, durch eine Feder getrieben, utomatisch wieder auf die Neutralstellung zurück gesprungen. Um den Schlitten nach vorne zu bewegen, musste das Poti richtung 0 Ohm verstellt werden. Je näher man an 0 Ohm heran gekommen ist, desto schneller bewegte sich der Schlitten. In dieser Richtung ist das Potentiometer nach dem loslassen nicht wieder zurück gesprungen.&lt;br /&gt;
Dieses Aufgabe übernimmt nun ein Digital-Potentiometer, dass über das 3-Wire Serial Interface angesteuert wird. Die Ansteuerng ist dabei denkbar einfach. Verwand ist das 3-Wire Serial Interface mit dem SPI. Es gibt eine CS-Leitung (Chip Select), die das Potentiometer bei Low-Potenzial aktiviert. Als zweite der drei Leitungen gibt es einen U/D-Eingang (Up/Down). Bei High-Potenzial wird der Wiper-Tab-Ausgang des Potentiometers niederohmiger (die Spannung wird höher), bei Low-Potenzial dann logischerweise hochohmiger.&lt;br /&gt;
Als drittes und letztes gibt es dann noch die INC-Leitung (Increment). Diese ist vergleichbar mit der Clock-Leitung bei der SPI-Schnittstelle. Bei jeder negativen Flanke wird der Widerstand je nach U/D-Pegel größer oder kleiner. &lt;br /&gt;
&lt;br /&gt;
[[Datei:BTM222.jpg|miniatur|Bluetooth-Modul BTM222]]&lt;br /&gt;
Nachdem die Grundfunktionalität der Firmware nun gegeben war, musste nun die drahtlose Kommunikation her. Diese Aufgabe übernimmt bei mir ein BTM222. Es hat den Vorteil, dass es eine große Reichweite hat (Class1: 100m) und einfach anzusteuern ist. Um eine UART-Funkbrücke zu realisieren, muss man nur die Rx- und Tx-Pins des Moduls mit den Tx- und Rx-Pins des Mikrocontrollers verbinden (Achtung: über Kreuz verbinden. Tx an Rx und Rx an Tx). Dann noch die Stromversorgung des Moduls und eine Antenne (bei mir ein paar cm Klingeldraht) und es kann los gehen. Für den XMC2GO habe ich dabei die von Uwe Becker bereitgestellte UART-Lib [http://mikrocontroller.bplaced.net/wordpress/?page_id=3809#I06 [4&amp;lt;nowiki&amp;gt;]&amp;lt;/nowiki&amp;gt;] genommen und leicht modifiziert. In der Lib sind TX auf P2.1 und RX auf R2.2 gelegt. Das macht auch Sinn, da damit die auf dem XMC2GO integrierte UART-to-USB Bridge angesprochen wird. Da ich jedoch TX und RX mit meinem BTM222 verbinden möchte, müssen diese auf die Pin-Leisten umgelegt werden. Ich habe mich nach einem Blick ins Datenblatt für die Pins P0.14 (RX) und P0.15 (TX) entschieden. Das hat den einfachen Grund, weil in der Lib die Input-Daten intern von DX3 (P2.2) auf DX0 umgeleitet werden. Da DX0 an P0.14 liegt, kann diese Umleitung einfach entfernt werden. Danach muss nur noch DOUT0 auf P0.15 umgeleitet werden und einer Kommunikation steht (fast) nichts mehr im Wege.&lt;br /&gt;
Da das Modul standardmäßig mit einer Baudrate von 19200bps arbeitet, in der UART-Lib aber 115200bps eingestellt sind, muss nun eines von beidem angepasst werden. Ich habe mich dafür entschieden, die Baudrate des Moduls anzupassen. Dafür habe ich einen USB-UART-Wandler an die Tx- und Rx-Pins angeschlossen und den Befehl ATL5 über das Programm hTerm an des Bluetooth-Modul gesendet. Damit wird auch auf dem BTM222 eine Baudrate von 115200bps eingestellt und XMC2GO und BTM222 können kommunizieren.&lt;br /&gt;
&lt;br /&gt;
Soweit so gut. Jetzt &#039;nur&#039; noch die Android App. Zum testen habe ich mich damit begnügt, mir eine App mit dem MIT App Inventor 2 [http://ai2.appinventor.mit.edu/ [5&amp;lt;nowiki&amp;gt;]&amp;lt;/nowiki&amp;gt;] zu erstellen. Dies ist eine kostenlose cloudbasierte Entwicklungsumgebung nach dem Baukastenprinzip, mit der man &#039;auf die Schnelle&#039; Apps für Android-Geräte erstellen kann. Benötigt wird nur ein Google-Account (den man für den Android PlayStore ja sowiso braucht). Dabei werden die verschiedenen Module und Logig-Einheiten als Puzzleteile dargestellt, die man dann zusammen stellen kann. Meiner Meinung nach reicht dies für kleinere Projekte durchaus aus, wird bei etwas mehr Umfang aber sehr schnell unübersichtlich. Die App, die ich mit diesem System erstellt habe, soll momentan nur dafür verwendet werden, die Technik des Projekts auf Herz und Nieren zu testen. Die eigentliche Steuerungsapp werde ich höchstwarscheinlich in einer richtigen IDE erstellen.&lt;br /&gt;
&lt;br /&gt;
Ich hoffe, ich konnte euch mein Projekt etwas näher bringen und der eine oder andere kann vielleicht noch einen Codeschnipsel oder eine Idee für ein eigenes Projekt übernehmen. &lt;br /&gt;
&lt;br /&gt;
Ich möchte an dieser Stelle noch darauf hinweisen, dass sich das ganze Projekt noch in der Erprobungsphase befindet und es noch einige Bugs und sicherlich auch noch die eine oder andere Änderung an der Hardware gibt. Beispielsweise ist mir bewusst, dass es nicht optimal ist, die 5V-Signale der Maschine durch einen Spannungsteiler auf 3,3V zu bringen. Für die nächste Hardware-Version ist schon ein Levelshifter eingeplant :-)&lt;br /&gt;
&lt;br /&gt;
== Downloads ==&lt;br /&gt;
&lt;br /&gt;
* [http://www.mikrocontroller.net/wikifiles/e/e0/Stapelschneider.zip Sourcecode XMC2GO]&lt;br /&gt;
* [http://www.mikrocontroller.net/wikifiles/0/04/IDEAL_Steuerung.aia Android App AI2 Projekt]  &lt;br /&gt;
* [http://www.mikrocontroller.net/wikifiles/b/b4/Stapelschneider_XMC2GO.pdf Schaltplan]&lt;br /&gt;
&lt;br /&gt;
== Bilder zum Projekt ==&lt;br /&gt;
&lt;br /&gt;
&amp;lt;gallery&amp;gt;&lt;br /&gt;
Datei:Schreibtisch.jpg|Erste Test der fertigen Schaltung auf dem Schreibtisch&lt;br /&gt;
Datei:Eingebaut.jpg|Schaltung mit Maschine verbunden&lt;br /&gt;
Datei:App-Blocks.PNG|Codebausteine im MIT App Inventor 2&lt;br /&gt;
Datei:App-Designer.PNG|Frontent Designer im MIT App Inventor 2&lt;br /&gt;
Datei:AndroidApp.png|Screenshot der fertigen App&lt;br /&gt;
&amp;lt;/gallery&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Siehe auch ==&lt;br /&gt;
&lt;br /&gt;
* [http://www2.keil.com/infineon/mdk/ [1&amp;lt;nowiki&amp;gt;]&amp;lt;/nowiki&amp;gt; http://www2.keil.com/infineon/mdk/]&lt;br /&gt;
* [http://www.infineonforums.com/ [2&amp;lt;nowiki&amp;gt;]&amp;lt;/nowiki&amp;gt; Infineonforums.com]&lt;br /&gt;
* [http://www.infineon.com/dgdl/Simple_XMC1200_ERU.exe?folderId=db3a30433580b3710135a47f3eb76c98&amp;amp;fileId=db3a30433efacd9a013f0efc19ad42d7&amp;amp;sd=t [3&amp;lt;nowiki&amp;gt;]&amp;lt;/nowiki&amp;gt; Infineon simple ERU Example] &lt;br /&gt;
* [http://mikrocontroller.bplaced.net/wordpress/?page_id=3809#I06 [4&amp;lt;nowiki&amp;gt;]&amp;lt;/nowiki&amp;gt; UART-Lib auf mikrocontroller.bplaced.net]&lt;br /&gt;
* [http://ai2.appinventor.mit.edu/ [5&amp;lt;nowiki&amp;gt;]&amp;lt;/nowiki&amp;gt; MIT App Inventor 2]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[Kategorie:Infineon_XMC_Design_Contest_2014| ]]&lt;br /&gt;
[[Kategorie:Infineon_XMC]]&lt;/div&gt;</summary>
		<author><name>213.179.131.90</name></author>
	</entry>
	<entry>
		<id>https://www.mikrocontroller.net/index.php?title=Strukturierte_Programmierung_auf_Mikrocontrollern&amp;diff=92171</id>
		<title>Strukturierte Programmierung auf Mikrocontrollern</title>
		<link rel="alternate" type="text/html" href="https://www.mikrocontroller.net/index.php?title=Strukturierte_Programmierung_auf_Mikrocontrollern&amp;diff=92171"/>
		<updated>2016-03-02T10:49:29Z</updated>

		<summary type="html">&lt;p&gt;213.179.131.90: /* Benennung von Variablen, Makros, Nutzung von Anweisungen */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Grundlegendes ==&lt;br /&gt;
&lt;br /&gt;
In diesem Artikel sollen die Grundlagen der saubere Aufteilung eines Programms in Module, Schichten und Strukturen erklären, besonders bezogen auf Mikrocontroller.&lt;br /&gt;
&lt;br /&gt;
Leider fällt im Forum oft auf, dass sehr gerne einfach alles in eine C-Datei &amp;quot;geklatscht&amp;quot; wird und fertig, das mag für kleinere Programme halbwegs funktionieren, bei größeren Projekten verliert man jedoch schnell die Übersicht und die Wartbarkeit des Codes wird sehr schlecht.&lt;br /&gt;
&lt;br /&gt;
Für die stukturierte (professionelle) Programmierung sind 3 Faktoren von Bedeutung:&lt;br /&gt;
&lt;br /&gt;
== Versionsverwaltung ==&lt;br /&gt;
&lt;br /&gt;
Oft kommt es vor, dass man an einem Programm arbeitet und irgendwann nach einer Änderung gar nichts mehr funktioniert und man es, warum auch immer, nicht schafft, den alten Zustand wiederherzustellen. Labile Naturen werfen dann meist das Projekt einfach hin, echte Männer fangen von vorn an ;-). Beides ist keine Lösung. Besonders interessant wird es, wenn man mit mehreren Personen an einer Datei arbeiten möchte und mehrere zur gleichen Zeit auf der selben Datei arbeiten. Wenn jeder einfach speichert, bleiben nur die letzten Änderungen erhalten.&lt;br /&gt;
&lt;br /&gt;
Dies löst ein Versionsverwaltungssystem, auch Source Code Management (SCM) oder Version Control System (VCS) genannt. Bekannte Versionsverwaltungen sind RCS, CVS, SVN, GIT. Ich möchte mich hier auf SVN beschränken. Eine gute Grundlagenerklärung zur Funktion von SVN bietet der Wikipedia-Artikel [http://de.wikipedia.org/wiki/Subversion_(Software) Subversion]. Ich bitte den Leser, sich diesen Artikel gründlich zu Gemüte zu führen. Dort sind vor allem wichtige Grundbegriffe erklärt, die den Rahmen dieses Artikels sprengen würden.&lt;br /&gt;
&lt;br /&gt;
Wer unter Linux, Unix oder BSD-Varianten arbeitet, der hat unter allen bekannten Versionsverwaltungen die größte Auswahl. Selbst ein frühes Festlegen auf ein SCM ist nicht unumkehrbar, denn es gibt sogar Konverter, die später den ganzen Code-Baum samt Geschichte umwandeln in ein anderes SCM.&lt;br /&gt;
&lt;br /&gt;
=== Installation von SVN ===&lt;br /&gt;
&lt;br /&gt;
Unter Windows empfehle ich den Server [http://www.visualsvn.com/ VisualSVN] und den in die Windows-Oberfläche integrierten Client [http://tortoisesvn.net/ TortoiseSVN]. Unter einem Debian-Derivat (z.&amp;amp;nbsp;B. Kubuntu) installiert man einfach das Paket &#039;&#039;&#039;subversion&#039;&#039;&#039;. Es existieren auch für Linux graphische Clients, auf die ich hier nicht weiter eingehen möchte.&lt;br /&gt;
&lt;br /&gt;
=== Verwendung von SVN ===&lt;br /&gt;
&lt;br /&gt;
Zur Verwendung von SVN gibt es eine sehr gute Anleitung unter: [https://www.bsdwiki.de/Subversion BSDwiki].  Ein Versionsverwaltungssystem mag zunächst lästig erscheinen. Spätestens, nachdem man das erste Mal seine Software zerschossen hat, mag man es nicht mehr missen.&lt;br /&gt;
&lt;br /&gt;
== Dokumentation ==&lt;br /&gt;
&lt;br /&gt;
Wichtig ist auch eine gute Dokumentation des Codes. Der erste Schritt sind aussagekräftige Kommentare im Programmtext. &amp;quot;Aussagekräftig&amp;quot; bedeutet, das man nicht schreibt was die Codezeile macht, sondern was sie bedeutet:&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;schlecht&#039;&#039;&#039;:&amp;lt;BR&amp;gt;&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
maxTests = 5;       # Setze maxTests auf 5        &amp;lt;--- Ach was? Hätte ich jetzt nicht gedacht&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;gut&#039;&#039;&#039;:&amp;lt;BR&amp;gt;&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
maxTests = 5;       # Maximal 5 mal abfragen       &amp;lt;--- Ahh!&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Weiterhin wird vor allem für größere Sachen empfohlen, ein integriertes Dokumentationssystems zu verwenden. Hier wurden gute Erfahrungen mit [http://de.wikipedia.org/wiki/Doxygen Doxygen] gemacht. Dieses Programm wurde unter der GPL veröffentlicht und erzeugt u.A. auch sogannte Callgraphs&lt;br /&gt;
&lt;br /&gt;
== Formatierung des Quelltextes ==&lt;br /&gt;
&lt;br /&gt;
Um ein Programm gut und schnell verstehen zu können, muss auch der Quelltext sauber formatiert sein. Denn ein Programm schreibt man einmal, liest es aber viele Male. Dazu müssen ein paar grundlegende Formatierungsregeln beachtet und einheitlich umgesetzt werden.&lt;br /&gt;
&lt;br /&gt;
* Syntax highlighting: Die meisten Editoren und Entwicklungsumgebungen unterstützen das farbige Hervorheben von Schlüsselwörtern. Das erleichtert die Lesbarkeit deutlich. Vor allem Kommentare sind somit leichter lokalisierbar.&lt;br /&gt;
* Einrückung: Bei While oder For -Schleife, If-Abfragen oder switch-Anweisungen sollen die Blöcke stets eingerückt werden, um die logische Struktur darzustellen. Dadurch sieht man auch leichter vergessene Klammern oder falsche logische Zuordung in verketteten if-Anweisungen.&lt;br /&gt;
* Begrenzung der Zeilenlänge auf 80-100 Zeichen&lt;br /&gt;
* Tabulatoren als Leerzeichen einfügen lassen: Das können die Editoren heute allein. Der Vorteil ist, dass der Quelltext danach immer gleich aussieht, und nicht auf einem anderen Editor mit anderer Tabulatoreinstellung verschoben aussieht.&lt;br /&gt;
&lt;br /&gt;
=== Benennung von Variablen, Makros, Nutzung von Anweisungen ===&lt;br /&gt;
&lt;br /&gt;
* selbsterklärende Funktions- und Variablennamen ersparen einem 100000 Kommentare&lt;br /&gt;
* Variablennamen sollen in erster Linie den Inhalt einer Variablen beschreiben, nicht ihren Datentyp.&lt;br /&gt;
* Defines komplett in GROSSBUCHSTABEN&lt;br /&gt;
* Namen von Variablen und Funktionen bzw. Methoden in Kleinbuchstaben; Worttrennung mit Unterstrich oder CamelCase&lt;br /&gt;
* Namen wie i, j, k für Iteratoren für Zählschleifen&lt;br /&gt;
* Variablen wie x, y, z für Positionen&lt;br /&gt;
* bei Arrays z.B. einkaufsPreis[i] oder einkaufsPreis[index] verwenden. i bzw. index sind übliche Namen um aus einem Array ein einzelnes Element zu identifizieren.&lt;br /&gt;
* Variablen und Makros so lokal wie möglich halten&lt;br /&gt;
* mit globalen Variablen sparsam umgehen und diese auch im Namen kennzeichnen, z. B. den Modulnamen voranstellen &#039;i8_LOG_Position&#039;&lt;br /&gt;
* Vermeidung langer Funktionen / Aufspalten in kleinere Funktionen und Bibliotheken: Verwendest du den gleichen Code an verschiedenen Stellen lohnt es sich diesen in eine Funktion auszulagern.&lt;br /&gt;
* Eine Funktion löst genau eine Aufgabenstellung&lt;br /&gt;
* Funktionen sollen nur das machen, was der Funktionsname erwarten lässt.&lt;br /&gt;
* Wiederverwendbarkeit durch Funktionen, keine doppelten Codeteile, für Geschwindigkeit notfalls #inline verwenden&lt;br /&gt;
* kurze und knackige Berechnungen, keinen Spaghetticode; Werden in der Berechnung Konstanten verwendet, dann am besten einen Kommentar dazu (z. B. b = a*3.6e6 // 3.6e6 ist Millisekunden pro Stunde)&lt;br /&gt;
* statt ?: am besten Verzweigungen verwenden, da dieser oft nicht bekannt ist und auch nur noch selten verwendet wird.&lt;br /&gt;
* Leerzeichen und Leerzeilen kosten kein Geld! Aber bitte nicht tonnenweise!&lt;br /&gt;
* Kommentare schreibt man für sich selbst, für später&lt;br /&gt;
* Kommentare sofort schreiben, hinterher ist man zu faul und nicht mehr zu 100 % im Problem vertieft&lt;br /&gt;
* Je genialer die Idee, um so nötiger der Kommentar.&lt;br /&gt;
* Zusammenhänge dokumentieren. Die erschliessen sich nicht aus den paar Zeilen Code, auf die man gerade schaut!&lt;br /&gt;
* Kommentare sollen die &#039;Warum&#039;-Frage beantworten und nicht die &#039;Wie&#039;-Frage! Wie etwas gemacht wird, steht im Code. Aber dort steht nicht warum es gemacht wird.&lt;br /&gt;
* Kommentare nach dem Muster &amp;quot;Das ist eine for-Schleife&amp;quot; lösen maximal Schmunzeln aus, es sei denn es handelt sich um ein C-Lehrbuch. Solche Kommentare (&amp;quot;Hier beginnen die Variablen&amp;quot;, &amp;quot;Hier beginnen die Funktionen&amp;quot;, etc) lässt man besser. Jeder der mehr als 5 Stunden C programmiert erkennt eine for-Schleife auf Anhieb und wenn nicht soll er zuerst ein C-Buch studieren, ehe er sich an Code versucht.&lt;br /&gt;
* Die üblichen Regeln der Muttersprache sollten in den Stil einfließen&lt;br /&gt;
* einheitlicher Stil bei Formatierung und Namensgebung&lt;br /&gt;
* Vermeidung voreiliger Optimierungen&lt;br /&gt;
&lt;br /&gt;
Beispiele&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
&lt;br /&gt;
/* Sicherung gegen doppeltes Einfuegen von Headerfiles */&lt;br /&gt;
#ifndef HEADER_FILE_NAME&lt;br /&gt;
#define HEADER_FILE_NAME&lt;br /&gt;
&lt;br /&gt;
// Das Headerfile&lt;br /&gt;
&lt;br /&gt;
#endif&lt;br /&gt;
&lt;br /&gt;
#define IN_GROSSBUCHSTABEN       // Caps mit underline&lt;br /&gt;
&lt;br /&gt;
int funktionsName(int param);    // CamelCase&lt;br /&gt;
&lt;br /&gt;
char varName;                    // CamelCase&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Modularisierung ==&lt;br /&gt;
&lt;br /&gt;
Nun zum wichtigsten Punkt: Ein Programm richtig in Module und Schichten zu unterteilen. Das ist aus verschiedenen Gründen notwendig.&lt;br /&gt;
&lt;br /&gt;
* Übersichtlichkeit: Vor allem bei größeren Sachen will und muss man den Überblick behalten. Dazu muss ein Programm sauber formatiert und strukturiert sein.&lt;br /&gt;
* Wartungsfreundlichkeit: Sowohl in der Entwicklungsphase als auch später bei der Erweiterung/Wartung ist ein gut modularisiertes Programm sehr wichtig&lt;br /&gt;
* Speicherverbrauch: Einen Ablauf, welcher mehrfach im Programm verwendet wird, packt man sinnvollerweise in eine Funktion. Dadurch wird nur einmal Speicherplatz benötigt, egal wie oft sie verwendet wird. &lt;br /&gt;
* Kapselung: Das Prinzip des Versteckens von Details steigert die Lesbarkeit deutlich, denn eine Funktion, die vielleicht drei Bildschirmseiten füllt, steht einfach als eine Anweisung in einer Zeile. Das ist vor allem deshalb von Vorteil, weil man sich nur einmal mit den Details einer Funktion beschäftigen muss, nämlich dann, wenn man sie erstellt. Für die Nutzung im Programm will man diese Information gar nicht haben, sie stören hier nur (Informationsüberfluß). &lt;br /&gt;
* Leistungsfähigkeit: Ein gut modularisiertes Programm erreicht ein bestimmte Funktionalität einfach und kompakt, weil die einzelnen Funktionen so angelegt sind, dass sie einfach und dennoch vielfältig verwendet werden können. Wichtig ist dabei die richtige Portionierung.&lt;br /&gt;
**Welche Funktion sollen immer zusammen sein, welche sollten getrennt werden?&lt;br /&gt;
**Wie gestaltet man die Parameter für eine Funktion sinnvoll?&lt;br /&gt;
* Testbarkeit: Das leidige Thema der Softwareentwicklung ist der Test. Dieser sollte theoretisch alle Fehler finden, praktisch wird das aber oft nicht erreicht. Da Software meist eine recht komplexe Sache ist, kann man sie nur sehr schwer als Gesamtwerk vollständig prüfen. Darum müssen zuerst die Teile einzeln getestet werden. Ein gut modularisiertes Programm kann man leichter testen.&lt;br /&gt;
&lt;br /&gt;
== Beiträge im Forum ==&lt;br /&gt;
&lt;br /&gt;
*[http://www.mikrocontroller.net/topic/26550#new C++ CodeChecking (Style,...)]&lt;br /&gt;
*[http://www.mikrocontroller.net/topic/132304#new Tutorial für _sauberen_ C-Code]&lt;br /&gt;
*[[Erweiterte LCD-Ansteuerung]]: Artikel mit einem einfachen Beispiel für strukturierte Programmierung&lt;br /&gt;
&lt;br /&gt;
== Weblinks ==&lt;br /&gt;
&lt;br /&gt;
* [http://www.gimpel.com/html/pcl.htm PC-lint, ein Analyseprogramm für C-Code]&lt;br /&gt;
* [http://www.chris-lott.org/resources/cstyle/indhill-cstyle.html Recommended C Style and Coding Standards, engl.]&lt;br /&gt;
* [http://www.jetcafe.org/jim/c-style.html Standards and Style for Coding in ANSI C, engl.]&lt;br /&gt;
* [http://de.wikipedia.org/wiki/Programmierstil Wikipediaartikel über Programmierstil]&lt;br /&gt;
* [http://www.campwoodsw.com/sourcemonitor.html Tool zur statischen Codeanalyse u.a. für C/C++]&lt;br /&gt;
*[http://en.wikipedia.org/wiki/Program_optimization Program optimization] auf Wikipedia, engl.&lt;br /&gt;
* [https://sites.google.com/site/artcfox/demystifying-the-tlc5940 demystifying-the-tlc5940] Umfassende Erklärung zur Ansteuerung eines TLC5940 sowie Hinweisen zum Vorgehen bei der Einarbeitung in neue Hard- und Software, engl.&lt;br /&gt;
* [http://kotaku.com/5975610/the-exceptional-beauty-of-doom-3s-source-code The Exceptional Beauty of Doom 3&#039;s Source Code] (engl.)&lt;br /&gt;
* [ftp://ftp.idsoftware.com/idstuff/doom3/source/CodeStyleConventions.doc CodeStyleConventions.doc] von iD Software für DOOM 3 &lt;br /&gt;
* [http://www.amazon.de/Weniger-schlecht-programmieren-Kathrin-Passig/dp/3897215675/ref=sr_1_1?ie=UTF8&amp;amp;qid=1444238128&amp;amp;sr=8-1&amp;amp;keywords=weniger+schlecht+programmieren Weniger schlecht programmieren], ISBN: 3897215675&lt;br /&gt;
* [http://c2.com/cgi/wiki?ThreeStarProgrammer ThreeStarProgrammer]: Warum man keinen hochkomplexen Code schreiben soll (engl.)&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[Kategorie:Algorithmen und Arithmetik]]&lt;br /&gt;
[[Kategorie:Mikrocontroller]]&lt;/div&gt;</summary>
		<author><name>213.179.131.90</name></author>
	</entry>
	<entry>
		<id>https://www.mikrocontroller.net/index.php?title=Strukturierte_Programmierung_auf_Mikrocontrollern&amp;diff=92169</id>
		<title>Strukturierte Programmierung auf Mikrocontrollern</title>
		<link rel="alternate" type="text/html" href="https://www.mikrocontroller.net/index.php?title=Strukturierte_Programmierung_auf_Mikrocontrollern&amp;diff=92169"/>
		<updated>2016-03-02T10:48:11Z</updated>

		<summary type="html">&lt;p&gt;213.179.131.90: /* Benennung von Variablen, Makros, Nutzung von Anweisungen */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Grundlegendes ==&lt;br /&gt;
&lt;br /&gt;
In diesem Artikel sollen die Grundlagen der saubere Aufteilung eines Programms in Module, Schichten und Strukturen erklären, besonders bezogen auf Mikrocontroller.&lt;br /&gt;
&lt;br /&gt;
Leider fällt im Forum oft auf, dass sehr gerne einfach alles in eine C-Datei &amp;quot;geklatscht&amp;quot; wird und fertig, das mag für kleinere Programme halbwegs funktionieren, bei größeren Projekten verliert man jedoch schnell die Übersicht und die Wartbarkeit des Codes wird sehr schlecht.&lt;br /&gt;
&lt;br /&gt;
Für die stukturierte (professionelle) Programmierung sind 3 Faktoren von Bedeutung:&lt;br /&gt;
&lt;br /&gt;
== Versionsverwaltung ==&lt;br /&gt;
&lt;br /&gt;
Oft kommt es vor, dass man an einem Programm arbeitet und irgendwann nach einer Änderung gar nichts mehr funktioniert und man es, warum auch immer, nicht schafft, den alten Zustand wiederherzustellen. Labile Naturen werfen dann meist das Projekt einfach hin, echte Männer fangen von vorn an ;-). Beides ist keine Lösung. Besonders interessant wird es, wenn man mit mehreren Personen an einer Datei arbeiten möchte und mehrere zur gleichen Zeit auf der selben Datei arbeiten. Wenn jeder einfach speichert, bleiben nur die letzten Änderungen erhalten.&lt;br /&gt;
&lt;br /&gt;
Dies löst ein Versionsverwaltungssystem, auch Source Code Management (SCM) oder Version Control System (VCS) genannt. Bekannte Versionsverwaltungen sind RCS, CVS, SVN, GIT. Ich möchte mich hier auf SVN beschränken. Eine gute Grundlagenerklärung zur Funktion von SVN bietet der Wikipedia-Artikel [http://de.wikipedia.org/wiki/Subversion_(Software) Subversion]. Ich bitte den Leser, sich diesen Artikel gründlich zu Gemüte zu führen. Dort sind vor allem wichtige Grundbegriffe erklärt, die den Rahmen dieses Artikels sprengen würden.&lt;br /&gt;
&lt;br /&gt;
Wer unter Linux, Unix oder BSD-Varianten arbeitet, der hat unter allen bekannten Versionsverwaltungen die größte Auswahl. Selbst ein frühes Festlegen auf ein SCM ist nicht unumkehrbar, denn es gibt sogar Konverter, die später den ganzen Code-Baum samt Geschichte umwandeln in ein anderes SCM.&lt;br /&gt;
&lt;br /&gt;
=== Installation von SVN ===&lt;br /&gt;
&lt;br /&gt;
Unter Windows empfehle ich den Server [http://www.visualsvn.com/ VisualSVN] und den in die Windows-Oberfläche integrierten Client [http://tortoisesvn.net/ TortoiseSVN]. Unter einem Debian-Derivat (z.&amp;amp;nbsp;B. Kubuntu) installiert man einfach das Paket &#039;&#039;&#039;subversion&#039;&#039;&#039;. Es existieren auch für Linux graphische Clients, auf die ich hier nicht weiter eingehen möchte.&lt;br /&gt;
&lt;br /&gt;
=== Verwendung von SVN ===&lt;br /&gt;
&lt;br /&gt;
Zur Verwendung von SVN gibt es eine sehr gute Anleitung unter: [https://www.bsdwiki.de/Subversion BSDwiki].  Ein Versionsverwaltungssystem mag zunächst lästig erscheinen. Spätestens, nachdem man das erste Mal seine Software zerschossen hat, mag man es nicht mehr missen.&lt;br /&gt;
&lt;br /&gt;
== Dokumentation ==&lt;br /&gt;
&lt;br /&gt;
Wichtig ist auch eine gute Dokumentation des Codes. Der erste Schritt sind aussagekräftige Kommentare im Programmtext. &amp;quot;Aussagekräftig&amp;quot; bedeutet, das man nicht schreibt was die Codezeile macht, sondern was sie bedeutet:&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;schlecht&#039;&#039;&#039;:&amp;lt;BR&amp;gt;&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
maxTests = 5;       # Setze maxTests auf 5        &amp;lt;--- Ach was? Hätte ich jetzt nicht gedacht&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;gut&#039;&#039;&#039;:&amp;lt;BR&amp;gt;&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
maxTests = 5;       # Maximal 5 mal abfragen       &amp;lt;--- Ahh!&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Weiterhin wird vor allem für größere Sachen empfohlen, ein integriertes Dokumentationssystems zu verwenden. Hier wurden gute Erfahrungen mit [http://de.wikipedia.org/wiki/Doxygen Doxygen] gemacht. Dieses Programm wurde unter der GPL veröffentlicht und erzeugt u.A. auch sogannte Callgraphs&lt;br /&gt;
&lt;br /&gt;
== Formatierung des Quelltextes ==&lt;br /&gt;
&lt;br /&gt;
Um ein Programm gut und schnell verstehen zu können, muss auch der Quelltext sauber formatiert sein. Denn ein Programm schreibt man einmal, liest es aber viele Male. Dazu müssen ein paar grundlegende Formatierungsregeln beachtet und einheitlich umgesetzt werden.&lt;br /&gt;
&lt;br /&gt;
* Syntax highlighting: Die meisten Editoren und Entwicklungsumgebungen unterstützen das farbige Hervorheben von Schlüsselwörtern. Das erleichtert die Lesbarkeit deutlich. Vor allem Kommentare sind somit leichter lokalisierbar.&lt;br /&gt;
* Einrückung: Bei While oder For -Schleife, If-Abfragen oder switch-Anweisungen sollen die Blöcke stets eingerückt werden, um die logische Struktur darzustellen. Dadurch sieht man auch leichter vergessene Klammern oder falsche logische Zuordung in verketteten if-Anweisungen.&lt;br /&gt;
* Begrenzung der Zeilenlänge auf 80-100 Zeichen&lt;br /&gt;
* Tabulatoren als Leerzeichen einfügen lassen: Das können die Editoren heute allein. Der Vorteil ist, dass der Quelltext danach immer gleich aussieht, und nicht auf einem anderen Editor mit anderer Tabulatoreinstellung verschoben aussieht.&lt;br /&gt;
&lt;br /&gt;
=== Benennung von Variablen, Makros, Nutzung von Anweisungen ===&lt;br /&gt;
&lt;br /&gt;
* selbsterklärende Funktions- und Variablennamen ersparen einem 100000 Kommentare&lt;br /&gt;
* Variablennamen sollen in erster Linie den Inhalt einer Variablen beschreiben, nicht ihren Datentyp.&lt;br /&gt;
* Defines komplett in GROSSBUCHSTABEN&lt;br /&gt;
* Namen von Variablen und Funktionen bzw. Methoden in Kleinbuchstaben; Worttrennung mit Unterstrich oder CamelCase&lt;br /&gt;
* Namen wie i, j, k für Iteratoren für Zählschleifen&lt;br /&gt;
* Variablen wie x, y, z für Positionen&lt;br /&gt;
* bei Arrays z.B. einkaufsPreis[i] oder einkaufsPreis[index] verwenden. i bzw. index sind übliche Namen um aus einem Array ein einzelnes Element zu identifizieren.&lt;br /&gt;
* Variablen und Makros so lokal wie möglich halten&lt;br /&gt;
* mit globalen Variablen sparsam umgehen und diese auch im Namen kennzeichnen, z. B. den Modulnamen voranstellen &#039;i8_LOG_Position&#039;&lt;br /&gt;
* Vermeidung langer Funktionen / Aufspalten in kleinere Funktionen und Bibliotheken: Verwendest du den gleichen Code an verschiedenen Stellen lohnt es sich diesen in eine Funktion auszulagern.&lt;br /&gt;
* Eine Funktion löst genau eine Aufgabenstellung&lt;br /&gt;
* Funktionen sollen nur das machen, was der Funktionsname erwarten lässt.&lt;br /&gt;
* Wiederverwendbarkeit durch Funktionen, keine doppelten Codeteile, für Geschwindigkeit notfalls #inline verwenden&lt;br /&gt;
* kurze und knackige Berechnungen, keinen Spaghetticode; Werden in der Berechnung Konstanten verwendet, dann am besten einen Kommentar dazu (z. B. b = a*3.6e6 // 3.6e6 ist Millisekunden pro Stunde)&lt;br /&gt;
* statt ?: am besten Verzweigungen verwenden, da dieser oft nicht bekannt ist und auch nur noch selten verwendet wird.&lt;br /&gt;
* Leerzeichen und Leerzeilen kosten kein Geld! Aber bitte nicht tonnenweise!&lt;br /&gt;
* Kommentare schreibt man für sich selbst, für später&lt;br /&gt;
* Kommentare sofort schreiben, hinterher ist man zu faul und nicht mehr zu 100 % im Problem vertieft&lt;br /&gt;
* Je genialer die Idee, um so nötiger der Kommentar.&lt;br /&gt;
* Zusammenhänge dokumentieren. Die erschliessen sich nicht aus den paar Zeilen Code, auf die man gerade schaut!&lt;br /&gt;
* Kommentare sollen die &#039;Warum&#039;-Frage beantworten und nicht die &#039;Wie&#039;-Frage! Wie etwas gemacht wird, steht im Code. Aber dort steht nicht warum es gemacht wird.&lt;br /&gt;
* Kommentare nach dem Muster &amp;quot;Das ist eine for-Schleife&amp;quot; lösen maximal Schmunzeln aus, es sei denn es handelt sich um ein C-Lehrbuch. Solche Kommentare (&amp;quot;Hier beginnen die Variablen&amp;quot;, &amp;quot;Hier beginnen die Funktionen&amp;quot;, etc) lässt man besser. Jeder der mehr als 5 Stunden C programmiert erkennt eine for-Schleife auf Anhieb und wenn nicht soll er zuerst ein C-Buch studieren, ehe er sich an Code versucht.&lt;br /&gt;
* Die üblichen Regeln der Muttersprache sollten in den Stil einfließen&lt;br /&gt;
* einheitlicher Stil bei Formatierung und Namensgebung&lt;br /&gt;
* Vermeidung voreiliger Optimierungen&lt;br /&gt;
&lt;br /&gt;
Beispiele&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
&lt;br /&gt;
/* Sicherung gegen doppeltes Einfuegen von Headerfiles */&lt;br /&gt;
#ifndef HEADER_FILE_NAME&lt;br /&gt;
#define HEADER_FILE_NAME&lt;br /&gt;
&lt;br /&gt;
// Das Headerfile&lt;br /&gt;
&lt;br /&gt;
#endif&lt;br /&gt;
&lt;br /&gt;
#define IN_GROSSBUCHSTABEN       // Caps mit underline&lt;br /&gt;
&lt;br /&gt;
int FunktionsName(int param);    // &amp;quot;grosses&amp;quot; CamelCase&lt;br /&gt;
&lt;br /&gt;
char varName;                    // &amp;quot;kleines&amp;quot; camelCase&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Modularisierung ==&lt;br /&gt;
&lt;br /&gt;
Nun zum wichtigsten Punkt: Ein Programm richtig in Module und Schichten zu unterteilen. Das ist aus verschiedenen Gründen notwendig.&lt;br /&gt;
&lt;br /&gt;
* Übersichtlichkeit: Vor allem bei größeren Sachen will und muss man den Überblick behalten. Dazu muss ein Programm sauber formatiert und strukturiert sein.&lt;br /&gt;
* Wartungsfreundlichkeit: Sowohl in der Entwicklungsphase als auch später bei der Erweiterung/Wartung ist ein gut modularisiertes Programm sehr wichtig&lt;br /&gt;
* Speicherverbrauch: Einen Ablauf, welcher mehrfach im Programm verwendet wird, packt man sinnvollerweise in eine Funktion. Dadurch wird nur einmal Speicherplatz benötigt, egal wie oft sie verwendet wird. &lt;br /&gt;
* Kapselung: Das Prinzip des Versteckens von Details steigert die Lesbarkeit deutlich, denn eine Funktion, die vielleicht drei Bildschirmseiten füllt, steht einfach als eine Anweisung in einer Zeile. Das ist vor allem deshalb von Vorteil, weil man sich nur einmal mit den Details einer Funktion beschäftigen muss, nämlich dann, wenn man sie erstellt. Für die Nutzung im Programm will man diese Information gar nicht haben, sie stören hier nur (Informationsüberfluß). &lt;br /&gt;
* Leistungsfähigkeit: Ein gut modularisiertes Programm erreicht ein bestimmte Funktionalität einfach und kompakt, weil die einzelnen Funktionen so angelegt sind, dass sie einfach und dennoch vielfältig verwendet werden können. Wichtig ist dabei die richtige Portionierung.&lt;br /&gt;
**Welche Funktion sollen immer zusammen sein, welche sollten getrennt werden?&lt;br /&gt;
**Wie gestaltet man die Parameter für eine Funktion sinnvoll?&lt;br /&gt;
* Testbarkeit: Das leidige Thema der Softwareentwicklung ist der Test. Dieser sollte theoretisch alle Fehler finden, praktisch wird das aber oft nicht erreicht. Da Software meist eine recht komplexe Sache ist, kann man sie nur sehr schwer als Gesamtwerk vollständig prüfen. Darum müssen zuerst die Teile einzeln getestet werden. Ein gut modularisiertes Programm kann man leichter testen.&lt;br /&gt;
&lt;br /&gt;
== Beiträge im Forum ==&lt;br /&gt;
&lt;br /&gt;
*[http://www.mikrocontroller.net/topic/26550#new C++ CodeChecking (Style,...)]&lt;br /&gt;
*[http://www.mikrocontroller.net/topic/132304#new Tutorial für _sauberen_ C-Code]&lt;br /&gt;
*[[Erweiterte LCD-Ansteuerung]]: Artikel mit einem einfachen Beispiel für strukturierte Programmierung&lt;br /&gt;
&lt;br /&gt;
== Weblinks ==&lt;br /&gt;
&lt;br /&gt;
* [http://www.gimpel.com/html/pcl.htm PC-lint, ein Analyseprogramm für C-Code]&lt;br /&gt;
* [http://www.chris-lott.org/resources/cstyle/indhill-cstyle.html Recommended C Style and Coding Standards, engl.]&lt;br /&gt;
* [http://www.jetcafe.org/jim/c-style.html Standards and Style for Coding in ANSI C, engl.]&lt;br /&gt;
* [http://de.wikipedia.org/wiki/Programmierstil Wikipediaartikel über Programmierstil]&lt;br /&gt;
* [http://www.campwoodsw.com/sourcemonitor.html Tool zur statischen Codeanalyse u.a. für C/C++]&lt;br /&gt;
*[http://en.wikipedia.org/wiki/Program_optimization Program optimization] auf Wikipedia, engl.&lt;br /&gt;
* [https://sites.google.com/site/artcfox/demystifying-the-tlc5940 demystifying-the-tlc5940] Umfassende Erklärung zur Ansteuerung eines TLC5940 sowie Hinweisen zum Vorgehen bei der Einarbeitung in neue Hard- und Software, engl.&lt;br /&gt;
* [http://kotaku.com/5975610/the-exceptional-beauty-of-doom-3s-source-code The Exceptional Beauty of Doom 3&#039;s Source Code] (engl.)&lt;br /&gt;
* [ftp://ftp.idsoftware.com/idstuff/doom3/source/CodeStyleConventions.doc CodeStyleConventions.doc] von iD Software für DOOM 3 &lt;br /&gt;
* [http://www.amazon.de/Weniger-schlecht-programmieren-Kathrin-Passig/dp/3897215675/ref=sr_1_1?ie=UTF8&amp;amp;qid=1444238128&amp;amp;sr=8-1&amp;amp;keywords=weniger+schlecht+programmieren Weniger schlecht programmieren], ISBN: 3897215675&lt;br /&gt;
* [http://c2.com/cgi/wiki?ThreeStarProgrammer ThreeStarProgrammer]: Warum man keinen hochkomplexen Code schreiben soll (engl.)&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[Kategorie:Algorithmen und Arithmetik]]&lt;br /&gt;
[[Kategorie:Mikrocontroller]]&lt;/div&gt;</summary>
		<author><name>213.179.131.90</name></author>
	</entry>
	<entry>
		<id>https://www.mikrocontroller.net/index.php?title=Strukturierte_Programmierung_auf_Mikrocontrollern&amp;diff=92168</id>
		<title>Strukturierte Programmierung auf Mikrocontrollern</title>
		<link rel="alternate" type="text/html" href="https://www.mikrocontroller.net/index.php?title=Strukturierte_Programmierung_auf_Mikrocontrollern&amp;diff=92168"/>
		<updated>2016-03-02T10:46:19Z</updated>

		<summary type="html">&lt;p&gt;213.179.131.90: /* Benennung von Variablen, Makros, Nutzung von Anweisungen */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Grundlegendes ==&lt;br /&gt;
&lt;br /&gt;
In diesem Artikel sollen die Grundlagen der saubere Aufteilung eines Programms in Module, Schichten und Strukturen erklären, besonders bezogen auf Mikrocontroller.&lt;br /&gt;
&lt;br /&gt;
Leider fällt im Forum oft auf, dass sehr gerne einfach alles in eine C-Datei &amp;quot;geklatscht&amp;quot; wird und fertig, das mag für kleinere Programme halbwegs funktionieren, bei größeren Projekten verliert man jedoch schnell die Übersicht und die Wartbarkeit des Codes wird sehr schlecht.&lt;br /&gt;
&lt;br /&gt;
Für die stukturierte (professionelle) Programmierung sind 3 Faktoren von Bedeutung:&lt;br /&gt;
&lt;br /&gt;
== Versionsverwaltung ==&lt;br /&gt;
&lt;br /&gt;
Oft kommt es vor, dass man an einem Programm arbeitet und irgendwann nach einer Änderung gar nichts mehr funktioniert und man es, warum auch immer, nicht schafft, den alten Zustand wiederherzustellen. Labile Naturen werfen dann meist das Projekt einfach hin, echte Männer fangen von vorn an ;-). Beides ist keine Lösung. Besonders interessant wird es, wenn man mit mehreren Personen an einer Datei arbeiten möchte und mehrere zur gleichen Zeit auf der selben Datei arbeiten. Wenn jeder einfach speichert, bleiben nur die letzten Änderungen erhalten.&lt;br /&gt;
&lt;br /&gt;
Dies löst ein Versionsverwaltungssystem, auch Source Code Management (SCM) oder Version Control System (VCS) genannt. Bekannte Versionsverwaltungen sind RCS, CVS, SVN, GIT. Ich möchte mich hier auf SVN beschränken. Eine gute Grundlagenerklärung zur Funktion von SVN bietet der Wikipedia-Artikel [http://de.wikipedia.org/wiki/Subversion_(Software) Subversion]. Ich bitte den Leser, sich diesen Artikel gründlich zu Gemüte zu führen. Dort sind vor allem wichtige Grundbegriffe erklärt, die den Rahmen dieses Artikels sprengen würden.&lt;br /&gt;
&lt;br /&gt;
Wer unter Linux, Unix oder BSD-Varianten arbeitet, der hat unter allen bekannten Versionsverwaltungen die größte Auswahl. Selbst ein frühes Festlegen auf ein SCM ist nicht unumkehrbar, denn es gibt sogar Konverter, die später den ganzen Code-Baum samt Geschichte umwandeln in ein anderes SCM.&lt;br /&gt;
&lt;br /&gt;
=== Installation von SVN ===&lt;br /&gt;
&lt;br /&gt;
Unter Windows empfehle ich den Server [http://www.visualsvn.com/ VisualSVN] und den in die Windows-Oberfläche integrierten Client [http://tortoisesvn.net/ TortoiseSVN]. Unter einem Debian-Derivat (z.&amp;amp;nbsp;B. Kubuntu) installiert man einfach das Paket &#039;&#039;&#039;subversion&#039;&#039;&#039;. Es existieren auch für Linux graphische Clients, auf die ich hier nicht weiter eingehen möchte.&lt;br /&gt;
&lt;br /&gt;
=== Verwendung von SVN ===&lt;br /&gt;
&lt;br /&gt;
Zur Verwendung von SVN gibt es eine sehr gute Anleitung unter: [https://www.bsdwiki.de/Subversion BSDwiki].  Ein Versionsverwaltungssystem mag zunächst lästig erscheinen. Spätestens, nachdem man das erste Mal seine Software zerschossen hat, mag man es nicht mehr missen.&lt;br /&gt;
&lt;br /&gt;
== Dokumentation ==&lt;br /&gt;
&lt;br /&gt;
Wichtig ist auch eine gute Dokumentation des Codes. Der erste Schritt sind aussagekräftige Kommentare im Programmtext. &amp;quot;Aussagekräftig&amp;quot; bedeutet, das man nicht schreibt was die Codezeile macht, sondern was sie bedeutet:&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;schlecht&#039;&#039;&#039;:&amp;lt;BR&amp;gt;&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
maxTests = 5;       # Setze maxTests auf 5        &amp;lt;--- Ach was? Hätte ich jetzt nicht gedacht&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;gut&#039;&#039;&#039;:&amp;lt;BR&amp;gt;&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
maxTests = 5;       # Maximal 5 mal abfragen       &amp;lt;--- Ahh!&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Weiterhin wird vor allem für größere Sachen empfohlen, ein integriertes Dokumentationssystems zu verwenden. Hier wurden gute Erfahrungen mit [http://de.wikipedia.org/wiki/Doxygen Doxygen] gemacht. Dieses Programm wurde unter der GPL veröffentlicht und erzeugt u.A. auch sogannte Callgraphs&lt;br /&gt;
&lt;br /&gt;
== Formatierung des Quelltextes ==&lt;br /&gt;
&lt;br /&gt;
Um ein Programm gut und schnell verstehen zu können, muss auch der Quelltext sauber formatiert sein. Denn ein Programm schreibt man einmal, liest es aber viele Male. Dazu müssen ein paar grundlegende Formatierungsregeln beachtet und einheitlich umgesetzt werden.&lt;br /&gt;
&lt;br /&gt;
* Syntax highlighting: Die meisten Editoren und Entwicklungsumgebungen unterstützen das farbige Hervorheben von Schlüsselwörtern. Das erleichtert die Lesbarkeit deutlich. Vor allem Kommentare sind somit leichter lokalisierbar.&lt;br /&gt;
* Einrückung: Bei While oder For -Schleife, If-Abfragen oder switch-Anweisungen sollen die Blöcke stets eingerückt werden, um die logische Struktur darzustellen. Dadurch sieht man auch leichter vergessene Klammern oder falsche logische Zuordung in verketteten if-Anweisungen.&lt;br /&gt;
* Begrenzung der Zeilenlänge auf 80-100 Zeichen&lt;br /&gt;
* Tabulatoren als Leerzeichen einfügen lassen: Das können die Editoren heute allein. Der Vorteil ist, dass der Quelltext danach immer gleich aussieht, und nicht auf einem anderen Editor mit anderer Tabulatoreinstellung verschoben aussieht.&lt;br /&gt;
&lt;br /&gt;
=== Benennung von Variablen, Makros, Nutzung von Anweisungen ===&lt;br /&gt;
&lt;br /&gt;
* selbsterklärende Funktions- und Variablennamen ersparen einem 100000 Kommentare&lt;br /&gt;
* Variablennamen sollen in erster Linie den Inhalt einer Variablen beschreiben, nicht ihren Datentyp.&lt;br /&gt;
* Defines komplett in GROSSBUCHSTABEN&lt;br /&gt;
* Namen von Variablen und Funktionen in Kleinbuchstaben; Worttrennung mit Unterstrich oder CamelCase&lt;br /&gt;
* Namen wie i, j, k für Iteratoren für Zählschleifen&lt;br /&gt;
* Variablen wie x, y, z für Positionen&lt;br /&gt;
* bei Arrays z.B. einkaufsPreis[i] oder einkaufsPreis[index] verwenden. i bzw. index sind übliche Namen um aus einem Array ein einzelnes Element zu identifizieren.&lt;br /&gt;
* Variablen und Makros so lokal wie möglich halten&lt;br /&gt;
* mit globalen Variablen sparsam umgehen und diese auch im Namen kennzeichnen, z. B. den Modulnamen voranstellen &#039;i8_LOG_Position&#039;&lt;br /&gt;
* Vermeidung langer Funktionen / Aufspalten in kleinere Funktionen und Bibliotheken: Verwendest du den gleichen Code an verschiedenen Stellen lohnt es sich diesen in eine Funktion auszulagern.&lt;br /&gt;
* Eine Funktion löst genau eine Aufgabenstellung&lt;br /&gt;
* Funktionen sollen nur das machen, was der Funktionsname erwarten lässt.&lt;br /&gt;
* Wiederverwendbarkeit durch Funktionen, keine doppelten Codeteile, für Geschwindigkeit notfalls #inline verwenden&lt;br /&gt;
* kurze und knackige Berechnungen, keinen Spaghetticode; Werden in der Berechnung Konstanten verwendet, dann am besten einen Kommentar dazu (z. B. b = a*3.6e6 // 3.6e6 ist Millisekunden pro Stunde)&lt;br /&gt;
* statt ?: am besten Verzweigungen verwenden, da dieser oft nicht bekannt ist und auch nur noch selten verwendet wird.&lt;br /&gt;
* Leerzeichen und Leerzeilen kosten kein Geld! Aber bitte nicht tonnenweise!&lt;br /&gt;
* Kommentare schreibt man für sich selbst, für später&lt;br /&gt;
* Kommentare sofort schreiben, hinterher ist man zu faul und nicht mehr zu 100 % im Problem vertieft&lt;br /&gt;
* Je genialer die Idee, um so nötiger der Kommentar.&lt;br /&gt;
* Zusammenhänge dokumentieren. Die erschliessen sich nicht aus den paar Zeilen Code, auf die man gerade schaut!&lt;br /&gt;
* Kommentare sollen die &#039;Warum&#039;-Frage beantworten und nicht die &#039;Wie&#039;-Frage! Wie etwas gemacht wird, steht im Code. Aber dort steht nicht warum es gemacht wird.&lt;br /&gt;
* Kommentare nach dem Muster &amp;quot;Das ist eine for-Schleife&amp;quot; lösen maximal Schmunzeln aus, es sei denn es handelt sich um ein C-Lehrbuch. Solche Kommentare (&amp;quot;Hier beginnen die Variablen&amp;quot;, &amp;quot;Hier beginnen die Funktionen&amp;quot;, etc) lässt man besser. Jeder der mehr als 5 Stunden C programmiert erkennt eine for-Schleife auf Anhieb und wenn nicht soll er zuerst ein C-Buch studieren, ehe er sich an Code versucht.&lt;br /&gt;
* Die üblichen Regeln der Muttersprache sollten in den Stil einfließen&lt;br /&gt;
* einheitlicher Stil bei Formatierung und Namensgebung&lt;br /&gt;
* Vermeidung voreiliger Optimierungen&lt;br /&gt;
&lt;br /&gt;
Beispiele&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
&lt;br /&gt;
/* Sicherung gegen doppeltes Einfuegen von Headerfiles */&lt;br /&gt;
#ifndef HEADER_FILE_NAME&lt;br /&gt;
#define HEADER_FILE_NAME&lt;br /&gt;
&lt;br /&gt;
// Das Headerfile&lt;br /&gt;
&lt;br /&gt;
#endif&lt;br /&gt;
&lt;br /&gt;
#define IN_GROSSBUCHSTABEN       // Caps mit underline&lt;br /&gt;
&lt;br /&gt;
int FunktionsName(int param);    // &amp;quot;grosses&amp;quot; CamelCase&lt;br /&gt;
&lt;br /&gt;
char varName;                    // &amp;quot;kleines&amp;quot; camelCase&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Modularisierung ==&lt;br /&gt;
&lt;br /&gt;
Nun zum wichtigsten Punkt: Ein Programm richtig in Module und Schichten zu unterteilen. Das ist aus verschiedenen Gründen notwendig.&lt;br /&gt;
&lt;br /&gt;
* Übersichtlichkeit: Vor allem bei größeren Sachen will und muss man den Überblick behalten. Dazu muss ein Programm sauber formatiert und strukturiert sein.&lt;br /&gt;
* Wartungsfreundlichkeit: Sowohl in der Entwicklungsphase als auch später bei der Erweiterung/Wartung ist ein gut modularisiertes Programm sehr wichtig&lt;br /&gt;
* Speicherverbrauch: Einen Ablauf, welcher mehrfach im Programm verwendet wird, packt man sinnvollerweise in eine Funktion. Dadurch wird nur einmal Speicherplatz benötigt, egal wie oft sie verwendet wird. &lt;br /&gt;
* Kapselung: Das Prinzip des Versteckens von Details steigert die Lesbarkeit deutlich, denn eine Funktion, die vielleicht drei Bildschirmseiten füllt, steht einfach als eine Anweisung in einer Zeile. Das ist vor allem deshalb von Vorteil, weil man sich nur einmal mit den Details einer Funktion beschäftigen muss, nämlich dann, wenn man sie erstellt. Für die Nutzung im Programm will man diese Information gar nicht haben, sie stören hier nur (Informationsüberfluß). &lt;br /&gt;
* Leistungsfähigkeit: Ein gut modularisiertes Programm erreicht ein bestimmte Funktionalität einfach und kompakt, weil die einzelnen Funktionen so angelegt sind, dass sie einfach und dennoch vielfältig verwendet werden können. Wichtig ist dabei die richtige Portionierung.&lt;br /&gt;
**Welche Funktion sollen immer zusammen sein, welche sollten getrennt werden?&lt;br /&gt;
**Wie gestaltet man die Parameter für eine Funktion sinnvoll?&lt;br /&gt;
* Testbarkeit: Das leidige Thema der Softwareentwicklung ist der Test. Dieser sollte theoretisch alle Fehler finden, praktisch wird das aber oft nicht erreicht. Da Software meist eine recht komplexe Sache ist, kann man sie nur sehr schwer als Gesamtwerk vollständig prüfen. Darum müssen zuerst die Teile einzeln getestet werden. Ein gut modularisiertes Programm kann man leichter testen.&lt;br /&gt;
&lt;br /&gt;
== Beiträge im Forum ==&lt;br /&gt;
&lt;br /&gt;
*[http://www.mikrocontroller.net/topic/26550#new C++ CodeChecking (Style,...)]&lt;br /&gt;
*[http://www.mikrocontroller.net/topic/132304#new Tutorial für _sauberen_ C-Code]&lt;br /&gt;
*[[Erweiterte LCD-Ansteuerung]]: Artikel mit einem einfachen Beispiel für strukturierte Programmierung&lt;br /&gt;
&lt;br /&gt;
== Weblinks ==&lt;br /&gt;
&lt;br /&gt;
* [http://www.gimpel.com/html/pcl.htm PC-lint, ein Analyseprogramm für C-Code]&lt;br /&gt;
* [http://www.chris-lott.org/resources/cstyle/indhill-cstyle.html Recommended C Style and Coding Standards, engl.]&lt;br /&gt;
* [http://www.jetcafe.org/jim/c-style.html Standards and Style for Coding in ANSI C, engl.]&lt;br /&gt;
* [http://de.wikipedia.org/wiki/Programmierstil Wikipediaartikel über Programmierstil]&lt;br /&gt;
* [http://www.campwoodsw.com/sourcemonitor.html Tool zur statischen Codeanalyse u.a. für C/C++]&lt;br /&gt;
*[http://en.wikipedia.org/wiki/Program_optimization Program optimization] auf Wikipedia, engl.&lt;br /&gt;
* [https://sites.google.com/site/artcfox/demystifying-the-tlc5940 demystifying-the-tlc5940] Umfassende Erklärung zur Ansteuerung eines TLC5940 sowie Hinweisen zum Vorgehen bei der Einarbeitung in neue Hard- und Software, engl.&lt;br /&gt;
* [http://kotaku.com/5975610/the-exceptional-beauty-of-doom-3s-source-code The Exceptional Beauty of Doom 3&#039;s Source Code] (engl.)&lt;br /&gt;
* [ftp://ftp.idsoftware.com/idstuff/doom3/source/CodeStyleConventions.doc CodeStyleConventions.doc] von iD Software für DOOM 3 &lt;br /&gt;
* [http://www.amazon.de/Weniger-schlecht-programmieren-Kathrin-Passig/dp/3897215675/ref=sr_1_1?ie=UTF8&amp;amp;qid=1444238128&amp;amp;sr=8-1&amp;amp;keywords=weniger+schlecht+programmieren Weniger schlecht programmieren], ISBN: 3897215675&lt;br /&gt;
* [http://c2.com/cgi/wiki?ThreeStarProgrammer ThreeStarProgrammer]: Warum man keinen hochkomplexen Code schreiben soll (engl.)&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[Kategorie:Algorithmen und Arithmetik]]&lt;br /&gt;
[[Kategorie:Mikrocontroller]]&lt;/div&gt;</summary>
		<author><name>213.179.131.90</name></author>
	</entry>
	<entry>
		<id>https://www.mikrocontroller.net/index.php?title=Strukturierte_Programmierung_auf_Mikrocontrollern&amp;diff=92166</id>
		<title>Strukturierte Programmierung auf Mikrocontrollern</title>
		<link rel="alternate" type="text/html" href="https://www.mikrocontroller.net/index.php?title=Strukturierte_Programmierung_auf_Mikrocontrollern&amp;diff=92166"/>
		<updated>2016-03-02T10:37:06Z</updated>

		<summary type="html">&lt;p&gt;213.179.131.90: /* Formatierung des Quelltextes */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Grundlegendes ==&lt;br /&gt;
&lt;br /&gt;
In diesem Artikel sollen die Grundlagen der saubere Aufteilung eines Programms in Module, Schichten und Strukturen erklären, besonders bezogen auf Mikrocontroller.&lt;br /&gt;
&lt;br /&gt;
Leider fällt im Forum oft auf, dass sehr gerne einfach alles in eine C-Datei &amp;quot;geklatscht&amp;quot; wird und fertig, das mag für kleinere Programme halbwegs funktionieren, bei größeren Projekten verliert man jedoch schnell die Übersicht und die Wartbarkeit des Codes wird sehr schlecht.&lt;br /&gt;
&lt;br /&gt;
Für die stukturierte (professionelle) Programmierung sind 3 Faktoren von Bedeutung:&lt;br /&gt;
&lt;br /&gt;
== Versionsverwaltung ==&lt;br /&gt;
&lt;br /&gt;
Oft kommt es vor, dass man an einem Programm arbeitet und irgendwann nach einer Änderung gar nichts mehr funktioniert und man es, warum auch immer, nicht schafft, den alten Zustand wiederherzustellen. Labile Naturen werfen dann meist das Projekt einfach hin, echte Männer fangen von vorn an ;-). Beides ist keine Lösung. Besonders interessant wird es, wenn man mit mehreren Personen an einer Datei arbeiten möchte und mehrere zur gleichen Zeit auf der selben Datei arbeiten. Wenn jeder einfach speichert, bleiben nur die letzten Änderungen erhalten.&lt;br /&gt;
&lt;br /&gt;
Dies löst ein Versionsverwaltungssystem, auch Source Code Management (SCM) oder Version Control System (VCS) genannt. Bekannte Versionsverwaltungen sind RCS, CVS, SVN, GIT. Ich möchte mich hier auf SVN beschränken. Eine gute Grundlagenerklärung zur Funktion von SVN bietet der Wikipedia-Artikel [http://de.wikipedia.org/wiki/Subversion_(Software) Subversion]. Ich bitte den Leser, sich diesen Artikel gründlich zu Gemüte zu führen. Dort sind vor allem wichtige Grundbegriffe erklärt, die den Rahmen dieses Artikels sprengen würden.&lt;br /&gt;
&lt;br /&gt;
Wer unter Linux, Unix oder BSD-Varianten arbeitet, der hat unter allen bekannten Versionsverwaltungen die größte Auswahl. Selbst ein frühes Festlegen auf ein SCM ist nicht unumkehrbar, denn es gibt sogar Konverter, die später den ganzen Code-Baum samt Geschichte umwandeln in ein anderes SCM.&lt;br /&gt;
&lt;br /&gt;
=== Installation von SVN ===&lt;br /&gt;
&lt;br /&gt;
Unter Windows empfehle ich den Server [http://www.visualsvn.com/ VisualSVN] und den in die Windows-Oberfläche integrierten Client [http://tortoisesvn.net/ TortoiseSVN]. Unter einem Debian-Derivat (z.&amp;amp;nbsp;B. Kubuntu) installiert man einfach das Paket &#039;&#039;&#039;subversion&#039;&#039;&#039;. Es existieren auch für Linux graphische Clients, auf die ich hier nicht weiter eingehen möchte.&lt;br /&gt;
&lt;br /&gt;
=== Verwendung von SVN ===&lt;br /&gt;
&lt;br /&gt;
Zur Verwendung von SVN gibt es eine sehr gute Anleitung unter: [https://www.bsdwiki.de/Subversion BSDwiki].  Ein Versionsverwaltungssystem mag zunächst lästig erscheinen. Spätestens, nachdem man das erste Mal seine Software zerschossen hat, mag man es nicht mehr missen.&lt;br /&gt;
&lt;br /&gt;
== Dokumentation ==&lt;br /&gt;
&lt;br /&gt;
Wichtig ist auch eine gute Dokumentation des Codes. Der erste Schritt sind aussagekräftige Kommentare im Programmtext. &amp;quot;Aussagekräftig&amp;quot; bedeutet, das man nicht schreibt was die Codezeile macht, sondern was sie bedeutet:&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;schlecht&#039;&#039;&#039;:&amp;lt;BR&amp;gt;&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
maxTests = 5;       # Setze maxTests auf 5        &amp;lt;--- Ach was? Hätte ich jetzt nicht gedacht&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;gut&#039;&#039;&#039;:&amp;lt;BR&amp;gt;&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
maxTests = 5;       # Maximal 5 mal abfragen       &amp;lt;--- Ahh!&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Weiterhin wird vor allem für größere Sachen empfohlen, ein integriertes Dokumentationssystems zu verwenden. Hier wurden gute Erfahrungen mit [http://de.wikipedia.org/wiki/Doxygen Doxygen] gemacht. Dieses Programm wurde unter der GPL veröffentlicht und erzeugt u.A. auch sogannte Callgraphs&lt;br /&gt;
&lt;br /&gt;
== Formatierung des Quelltextes ==&lt;br /&gt;
&lt;br /&gt;
Um ein Programm gut und schnell verstehen zu können, muss auch der Quelltext sauber formatiert sein. Denn ein Programm schreibt man einmal, liest es aber viele Male. Dazu müssen ein paar grundlegende Formatierungsregeln beachtet und einheitlich umgesetzt werden.&lt;br /&gt;
&lt;br /&gt;
* Syntax highlighting: Die meisten Editoren und Entwicklungsumgebungen unterstützen das farbige Hervorheben von Schlüsselwörtern. Das erleichtert die Lesbarkeit deutlich. Vor allem Kommentare sind somit leichter lokalisierbar.&lt;br /&gt;
* Einrückung: Bei While oder For -Schleife, If-Abfragen oder switch-Anweisungen sollen die Blöcke stets eingerückt werden, um die logische Struktur darzustellen. Dadurch sieht man auch leichter vergessene Klammern oder falsche logische Zuordung in verketteten if-Anweisungen.&lt;br /&gt;
* Begrenzung der Zeilenlänge auf eine angemessene Länge, da die Zeit der kleinen Monitore 4:3 Monitore vorbei ist greift hier die altbekannte 80..100 Zeichen Regel nicht mehr, dennoch sollte man sich einen Richtwert setzen, damit noch genügend Platz für Kommentare bleibt.&lt;br /&gt;
* Tabulatoren als Leerzeichen einfügen lassen: Das können die Editoren heute allein. Der Vorteil ist, dass der Quelltext danach immer gleich aussieht, und nicht auf einem anderen Editor mit anderer Tabulatoreinstellung verschoben aussieht.&lt;br /&gt;
&lt;br /&gt;
=== Benennung von Variablen, Makros, Nutzung von Anweisungen ===&lt;br /&gt;
&lt;br /&gt;
* selbsterklärende Funktions- und Variablennamen ersparen einem 100000 Kommentare&lt;br /&gt;
* Variablennamen sollen in erster Linie den Inhalt einer Variablen beschreiben, nicht ihren Datentyp.&lt;br /&gt;
* Defines komplett in GROSSBUCHSTABEN&lt;br /&gt;
* Variablennamen in Kleinbuchstaben mit Großbuchstaben für Wortblöcke&lt;br /&gt;
* Variablen wie i, j, k für übersichtliche, kurze Schleifen&lt;br /&gt;
* Variablen wie x, y, z für Positionen&lt;br /&gt;
* bei Arrays z.B. einkaufsPreis[i] oder einkaufsPreis[index] verwenden. i bzw. index sind übliche Namen um aus einem Array ein einzelnes Element zu identifizieren.&lt;br /&gt;
* Variablen und Makros so lokal wie möglich halten&lt;br /&gt;
* mit globalen Variablen sparsam umgehen und diese auch im Namen kennzeichnen&lt;br /&gt;
* Vermeidung langer Funktionen/Aufspalten in kleinere Funktionen und Bibliotheken&lt;br /&gt;
* Eine Funktion löst genau eine Aufgabenstellung&lt;br /&gt;
* Funktionen sollen nur das machen, was der Funktionsname erwarten lässt.&lt;br /&gt;
* Wiederverwendbarkeit durch Funktionen, keine doppelten Codeteile, für Geschwindigkeit notfalls #inline verwenden&lt;br /&gt;
* kurze und knackige Berechnungen, keinen Spaghetticode&lt;br /&gt;
* ?: - Operator nur bei kompakten Ausdrücken verwenden, sonst if/else&lt;br /&gt;
* Leerzeichen und Leerzeilen kosten kein Geld! Aber bitte nicht tonnenweise!&lt;br /&gt;
* Kommentare schreibt man für sich selbst, für später&lt;br /&gt;
* Kommentare sofort schreiben, hinterher ist man zu faul und nicht mehr zu 100 % im Problem vertieft&lt;br /&gt;
* Je genialer die Idee, um so nötiger der Kommentar.&lt;br /&gt;
* Zusammenhänge dokumentieren. Die erschliessen sich nicht aus den paar Zeilen Code, auf die man gerade schaut!&lt;br /&gt;
* Kommentare sollen die &#039;Warum&#039;-Frage beantworten und nicht die &#039;Wie&#039;-Frage! Wie etwas gemacht wird, steht im Code. Aber dort steht nicht warum es gemacht wird.&lt;br /&gt;
* Kommentare nach dem Muster &amp;quot;Das ist eine for-Schleife&amp;quot; lösen maximal Schmunzeln aus, es sei denn es handelt sich um ein C-Lehrbuch. Solche Kommentare (&amp;quot;Hier beginnen die Variablen&amp;quot;, &amp;quot;Hier beginnen die Funktionen&amp;quot;, etc) lässt man besser. Jeder der mehr als 5 Stunden C programmiert erkennt eine for-Schleife auf Anhieb und wenn nicht soll er zuerst ein C-Buch studieren, ehe er sich an Code versucht.&lt;br /&gt;
* Die üblichen Regeln der Muttersprache sollten in den Stil einfliessen (oder englisch, wenn&#039;s wirklich auch für andere sein soll) .&lt;br /&gt;
* einheitlicher Stil bei Formatierung und Namensgebung&lt;br /&gt;
* Vermeidung voreiliger Optimierungen&lt;br /&gt;
&lt;br /&gt;
Beispiele&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
&lt;br /&gt;
/* Sicherung gegen doppeltes Einfuegen von Headerfiles */&lt;br /&gt;
#ifndef HEADER_FILE_NAME&lt;br /&gt;
#define HEADER_FILE_NAME&lt;br /&gt;
&lt;br /&gt;
// Das Headerfile&lt;br /&gt;
&lt;br /&gt;
#endif&lt;br /&gt;
&lt;br /&gt;
#define IN_GROSSBUCHSTABEN       // Caps mit underline&lt;br /&gt;
&lt;br /&gt;
int FunktionsName(int param);    // &amp;quot;grosses&amp;quot; CamelCase&lt;br /&gt;
&lt;br /&gt;
char varName;                    // &amp;quot;kleines&amp;quot; camelCase&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Modularisierung ==&lt;br /&gt;
&lt;br /&gt;
Nun zum wichtigsten Punkt: Ein Programm richtig in Module und Schichten zu unterteilen. Das ist aus verschiedenen Gründen notwendig.&lt;br /&gt;
&lt;br /&gt;
* Übersichtlichkeit: Vor allem bei größeren Sachen will und muss man den Überblick behalten. Dazu muss ein Programm sauber formatiert und strukturiert sein.&lt;br /&gt;
* Wartungsfreundlichkeit: Sowohl in der Entwicklungsphase als auch später bei der Erweiterung/Wartung ist ein gut modularisiertes Programm sehr wichtig&lt;br /&gt;
* Speicherverbrauch: Einen Ablauf, welcher mehrfach im Programm verwendet wird, packt man sinnvollerweise in eine Funktion. Dadurch wird nur einmal Speicherplatz benötigt, egal wie oft sie verwendet wird. &lt;br /&gt;
* Kapselung: Das Prinzip des Versteckens von Details steigert die Lesbarkeit deutlich, denn eine Funktion, die vielleicht drei Bildschirmseiten füllt, steht einfach als eine Anweisung in einer Zeile. Das ist vor allem deshalb von Vorteil, weil man sich nur einmal mit den Details einer Funktion beschäftigen muss, nämlich dann, wenn man sie erstellt. Für die Nutzung im Programm will man diese Information gar nicht haben, sie stören hier nur (Informationsüberfluß). &lt;br /&gt;
* Leistungsfähigkeit: Ein gut modularisiertes Programm erreicht ein bestimmte Funktionalität einfach und kompakt, weil die einzelnen Funktionen so angelegt sind, dass sie einfach und dennoch vielfältig verwendet werden können. Wichtig ist dabei die richtige Portionierung.&lt;br /&gt;
**Welche Funktion sollen immer zusammen sein, welche sollten getrennt werden?&lt;br /&gt;
**Wie gestaltet man die Parameter für eine Funktion sinnvoll?&lt;br /&gt;
* Testbarkeit: Das leidige Thema der Softwareentwicklung ist der Test. Dieser sollte theoretisch alle Fehler finden, praktisch wird das aber oft nicht erreicht. Da Software meist eine recht komplexe Sache ist, kann man sie nur sehr schwer als Gesamtwerk vollständig prüfen. Darum müssen zuerst die Teile einzeln getestet werden. Ein gut modularisiertes Programm kann man leichter testen.&lt;br /&gt;
&lt;br /&gt;
== Beiträge im Forum ==&lt;br /&gt;
&lt;br /&gt;
*[http://www.mikrocontroller.net/topic/26550#new C++ CodeChecking (Style,...)]&lt;br /&gt;
*[http://www.mikrocontroller.net/topic/132304#new Tutorial für _sauberen_ C-Code]&lt;br /&gt;
*[[Erweiterte LCD-Ansteuerung]]: Artikel mit einem einfachen Beispiel für strukturierte Programmierung&lt;br /&gt;
&lt;br /&gt;
== Weblinks ==&lt;br /&gt;
&lt;br /&gt;
* [http://www.gimpel.com/html/pcl.htm PC-lint, ein Analyseprogramm für C-Code]&lt;br /&gt;
* [http://www.chris-lott.org/resources/cstyle/indhill-cstyle.html Recommended C Style and Coding Standards, engl.]&lt;br /&gt;
* [http://www.jetcafe.org/jim/c-style.html Standards and Style for Coding in ANSI C, engl.]&lt;br /&gt;
* [http://de.wikipedia.org/wiki/Programmierstil Wikipediaartikel über Programmierstil]&lt;br /&gt;
* [http://www.campwoodsw.com/sourcemonitor.html Tool zur statischen Codeanalyse u.a. für C/C++]&lt;br /&gt;
*[http://en.wikipedia.org/wiki/Program_optimization Program optimization] auf Wikipedia, engl.&lt;br /&gt;
* [https://sites.google.com/site/artcfox/demystifying-the-tlc5940 demystifying-the-tlc5940] Umfassende Erklärung zur Ansteuerung eines TLC5940 sowie Hinweisen zum Vorgehen bei der Einarbeitung in neue Hard- und Software, engl.&lt;br /&gt;
* [http://kotaku.com/5975610/the-exceptional-beauty-of-doom-3s-source-code The Exceptional Beauty of Doom 3&#039;s Source Code] (engl.)&lt;br /&gt;
* [ftp://ftp.idsoftware.com/idstuff/doom3/source/CodeStyleConventions.doc CodeStyleConventions.doc] von iD Software für DOOM 3 &lt;br /&gt;
* [http://www.amazon.de/Weniger-schlecht-programmieren-Kathrin-Passig/dp/3897215675/ref=sr_1_1?ie=UTF8&amp;amp;qid=1444238128&amp;amp;sr=8-1&amp;amp;keywords=weniger+schlecht+programmieren Weniger schlecht programmieren], ISBN: 3897215675&lt;br /&gt;
* [http://c2.com/cgi/wiki?ThreeStarProgrammer ThreeStarProgrammer]: Warum man keinen hochkomplexen Code schreiben soll (engl.)&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[Kategorie:Algorithmen und Arithmetik]]&lt;br /&gt;
[[Kategorie:Mikrocontroller]]&lt;/div&gt;</summary>
		<author><name>213.179.131.90</name></author>
	</entry>
	<entry>
		<id>https://www.mikrocontroller.net/index.php?title=Strukturierte_Programmierung_auf_Mikrocontrollern&amp;diff=92165</id>
		<title>Strukturierte Programmierung auf Mikrocontrollern</title>
		<link rel="alternate" type="text/html" href="https://www.mikrocontroller.net/index.php?title=Strukturierte_Programmierung_auf_Mikrocontrollern&amp;diff=92165"/>
		<updated>2016-03-02T10:36:34Z</updated>

		<summary type="html">&lt;p&gt;213.179.131.90: /* Formatierung des Quelltextes */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Grundlegendes ==&lt;br /&gt;
&lt;br /&gt;
In diesem Artikel sollen die Grundlagen der saubere Aufteilung eines Programms in Module, Schichten und Strukturen erklären, besonders bezogen auf Mikrocontroller.&lt;br /&gt;
&lt;br /&gt;
Leider fällt im Forum oft auf, dass sehr gerne einfach alles in eine C-Datei &amp;quot;geklatscht&amp;quot; wird und fertig, das mag für kleinere Programme halbwegs funktionieren, bei größeren Projekten verliert man jedoch schnell die Übersicht und die Wartbarkeit des Codes wird sehr schlecht.&lt;br /&gt;
&lt;br /&gt;
Für die stukturierte (professionelle) Programmierung sind 3 Faktoren von Bedeutung:&lt;br /&gt;
&lt;br /&gt;
== Versionsverwaltung ==&lt;br /&gt;
&lt;br /&gt;
Oft kommt es vor, dass man an einem Programm arbeitet und irgendwann nach einer Änderung gar nichts mehr funktioniert und man es, warum auch immer, nicht schafft, den alten Zustand wiederherzustellen. Labile Naturen werfen dann meist das Projekt einfach hin, echte Männer fangen von vorn an ;-). Beides ist keine Lösung. Besonders interessant wird es, wenn man mit mehreren Personen an einer Datei arbeiten möchte und mehrere zur gleichen Zeit auf der selben Datei arbeiten. Wenn jeder einfach speichert, bleiben nur die letzten Änderungen erhalten.&lt;br /&gt;
&lt;br /&gt;
Dies löst ein Versionsverwaltungssystem, auch Source Code Management (SCM) oder Version Control System (VCS) genannt. Bekannte Versionsverwaltungen sind RCS, CVS, SVN, GIT. Ich möchte mich hier auf SVN beschränken. Eine gute Grundlagenerklärung zur Funktion von SVN bietet der Wikipedia-Artikel [http://de.wikipedia.org/wiki/Subversion_(Software) Subversion]. Ich bitte den Leser, sich diesen Artikel gründlich zu Gemüte zu führen. Dort sind vor allem wichtige Grundbegriffe erklärt, die den Rahmen dieses Artikels sprengen würden.&lt;br /&gt;
&lt;br /&gt;
Wer unter Linux, Unix oder BSD-Varianten arbeitet, der hat unter allen bekannten Versionsverwaltungen die größte Auswahl. Selbst ein frühes Festlegen auf ein SCM ist nicht unumkehrbar, denn es gibt sogar Konverter, die später den ganzen Code-Baum samt Geschichte umwandeln in ein anderes SCM.&lt;br /&gt;
&lt;br /&gt;
=== Installation von SVN ===&lt;br /&gt;
&lt;br /&gt;
Unter Windows empfehle ich den Server [http://www.visualsvn.com/ VisualSVN] und den in die Windows-Oberfläche integrierten Client [http://tortoisesvn.net/ TortoiseSVN]. Unter einem Debian-Derivat (z.&amp;amp;nbsp;B. Kubuntu) installiert man einfach das Paket &#039;&#039;&#039;subversion&#039;&#039;&#039;. Es existieren auch für Linux graphische Clients, auf die ich hier nicht weiter eingehen möchte.&lt;br /&gt;
&lt;br /&gt;
=== Verwendung von SVN ===&lt;br /&gt;
&lt;br /&gt;
Zur Verwendung von SVN gibt es eine sehr gute Anleitung unter: [https://www.bsdwiki.de/Subversion BSDwiki].  Ein Versionsverwaltungssystem mag zunächst lästig erscheinen. Spätestens, nachdem man das erste Mal seine Software zerschossen hat, mag man es nicht mehr missen.&lt;br /&gt;
&lt;br /&gt;
== Dokumentation ==&lt;br /&gt;
&lt;br /&gt;
Wichtig ist auch eine gute Dokumentation des Codes. Der erste Schritt sind aussagekräftige Kommentare im Programmtext. &amp;quot;Aussagekräftig&amp;quot; bedeutet, das man nicht schreibt was die Codezeile macht, sondern was sie bedeutet:&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;schlecht&#039;&#039;&#039;:&amp;lt;BR&amp;gt;&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
maxTests = 5;       # Setze maxTests auf 5        &amp;lt;--- Ach was? Hätte ich jetzt nicht gedacht&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;gut&#039;&#039;&#039;:&amp;lt;BR&amp;gt;&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
maxTests = 5;       # Maximal 5 mal abfragen       &amp;lt;--- Ahh!&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Weiterhin wird vor allem für größere Sachen empfohlen, ein integriertes Dokumentationssystems zu verwenden. Hier wurden gute Erfahrungen mit [http://de.wikipedia.org/wiki/Doxygen Doxygen] gemacht. Dieses Programm wurde unter der GPL veröffentlicht und erzeugt u.A. auch sogannte Callgraphs&lt;br /&gt;
&lt;br /&gt;
== Formatierung des Quelltextes ==&lt;br /&gt;
&lt;br /&gt;
Um ein Programm gut und schnell verstehen zu können, muss auch der Quelltext sauber formatiert sein. Denn ein Programm schreibt man einmal, liest es aber viele Male. Dazu müssen ein paar grundlegende Formatierungsregeln beachtet und einheitlich umgesetzt werden.&lt;br /&gt;
&lt;br /&gt;
* Syntax highlighting: Die meisten Editoren und Entwicklungsumgebungen unterstützen das farbige Hervorheben von Schlüsselwörtern. Das erleichtert die Lesbarkeit deutlich. Vor allem Kommentare sind somit leichter lokalisierbar.&lt;br /&gt;
* Einrückung: Bei While oder For -Schleife, If-Abfragen oder switch-Anweisungen sollen die Blöcke stets eingerückt werden, um die logische Struktur darzustellen. Dadurch sieht man auch leichter vergessene Klammern oder falsche logische Zuordung in verketteten if-Anweisungen.&lt;br /&gt;
* Begrenzung der Zeilenlänge auf eine angemessene Länge, da die Zeit der kleinen Monitore 4:3 Monitore vorbei ist greif hier die altbekannte 80..100 Zeichen Regel nicht mehr, dennoch sollte man sich einen Richtwert setzen, damit noch genügend Platz für Kommentare bleibt.&lt;br /&gt;
* Tabulatoren als Leerzeichen einfügen lassen: Das können die Editoren heute allein. Der Vorteil ist, dass der Quelltext danach immer gleich aussieht, und nicht auf einem anderen Editor mit anderer Tabulatoreinstellung verschoben aussieht.&lt;br /&gt;
&lt;br /&gt;
=== Benennung von Variablen, Makros, Nutzung von Anweisungen ===&lt;br /&gt;
&lt;br /&gt;
* selbsterklärende Funktions- und Variablennamen ersparen einem 100000 Kommentare&lt;br /&gt;
* Variablennamen sollen in erster Linie den Inhalt einer Variablen beschreiben, nicht ihren Datentyp.&lt;br /&gt;
* Defines komplett in GROSSBUCHSTABEN&lt;br /&gt;
* Variablennamen in Kleinbuchstaben mit Großbuchstaben für Wortblöcke&lt;br /&gt;
* Variablen wie i, j, k für übersichtliche, kurze Schleifen&lt;br /&gt;
* Variablen wie x, y, z für Positionen&lt;br /&gt;
* bei Arrays z.B. einkaufsPreis[i] oder einkaufsPreis[index] verwenden. i bzw. index sind übliche Namen um aus einem Array ein einzelnes Element zu identifizieren.&lt;br /&gt;
* Variablen und Makros so lokal wie möglich halten&lt;br /&gt;
* mit globalen Variablen sparsam umgehen und diese auch im Namen kennzeichnen&lt;br /&gt;
* Vermeidung langer Funktionen/Aufspalten in kleinere Funktionen und Bibliotheken&lt;br /&gt;
* Eine Funktion löst genau eine Aufgabenstellung&lt;br /&gt;
* Funktionen sollen nur das machen, was der Funktionsname erwarten lässt.&lt;br /&gt;
* Wiederverwendbarkeit durch Funktionen, keine doppelten Codeteile, für Geschwindigkeit notfalls #inline verwenden&lt;br /&gt;
* kurze und knackige Berechnungen, keinen Spaghetticode&lt;br /&gt;
* ?: - Operator nur bei kompakten Ausdrücken verwenden, sonst if/else&lt;br /&gt;
* Leerzeichen und Leerzeilen kosten kein Geld! Aber bitte nicht tonnenweise!&lt;br /&gt;
* Kommentare schreibt man für sich selbst, für später&lt;br /&gt;
* Kommentare sofort schreiben, hinterher ist man zu faul und nicht mehr zu 100 % im Problem vertieft&lt;br /&gt;
* Je genialer die Idee, um so nötiger der Kommentar.&lt;br /&gt;
* Zusammenhänge dokumentieren. Die erschliessen sich nicht aus den paar Zeilen Code, auf die man gerade schaut!&lt;br /&gt;
* Kommentare sollen die &#039;Warum&#039;-Frage beantworten und nicht die &#039;Wie&#039;-Frage! Wie etwas gemacht wird, steht im Code. Aber dort steht nicht warum es gemacht wird.&lt;br /&gt;
* Kommentare nach dem Muster &amp;quot;Das ist eine for-Schleife&amp;quot; lösen maximal Schmunzeln aus, es sei denn es handelt sich um ein C-Lehrbuch. Solche Kommentare (&amp;quot;Hier beginnen die Variablen&amp;quot;, &amp;quot;Hier beginnen die Funktionen&amp;quot;, etc) lässt man besser. Jeder der mehr als 5 Stunden C programmiert erkennt eine for-Schleife auf Anhieb und wenn nicht soll er zuerst ein C-Buch studieren, ehe er sich an Code versucht.&lt;br /&gt;
* Die üblichen Regeln der Muttersprache sollten in den Stil einfliessen (oder englisch, wenn&#039;s wirklich auch für andere sein soll) .&lt;br /&gt;
* einheitlicher Stil bei Formatierung und Namensgebung&lt;br /&gt;
* Vermeidung voreiliger Optimierungen&lt;br /&gt;
&lt;br /&gt;
Beispiele&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
&lt;br /&gt;
/* Sicherung gegen doppeltes Einfuegen von Headerfiles */&lt;br /&gt;
#ifndef HEADER_FILE_NAME&lt;br /&gt;
#define HEADER_FILE_NAME&lt;br /&gt;
&lt;br /&gt;
// Das Headerfile&lt;br /&gt;
&lt;br /&gt;
#endif&lt;br /&gt;
&lt;br /&gt;
#define IN_GROSSBUCHSTABEN       // Caps mit underline&lt;br /&gt;
&lt;br /&gt;
int FunktionsName(int param);    // &amp;quot;grosses&amp;quot; CamelCase&lt;br /&gt;
&lt;br /&gt;
char varName;                    // &amp;quot;kleines&amp;quot; camelCase&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Modularisierung ==&lt;br /&gt;
&lt;br /&gt;
Nun zum wichtigsten Punkt: Ein Programm richtig in Module und Schichten zu unterteilen. Das ist aus verschiedenen Gründen notwendig.&lt;br /&gt;
&lt;br /&gt;
* Übersichtlichkeit: Vor allem bei größeren Sachen will und muss man den Überblick behalten. Dazu muss ein Programm sauber formatiert und strukturiert sein.&lt;br /&gt;
* Wartungsfreundlichkeit: Sowohl in der Entwicklungsphase als auch später bei der Erweiterung/Wartung ist ein gut modularisiertes Programm sehr wichtig&lt;br /&gt;
* Speicherverbrauch: Einen Ablauf, welcher mehrfach im Programm verwendet wird, packt man sinnvollerweise in eine Funktion. Dadurch wird nur einmal Speicherplatz benötigt, egal wie oft sie verwendet wird. &lt;br /&gt;
* Kapselung: Das Prinzip des Versteckens von Details steigert die Lesbarkeit deutlich, denn eine Funktion, die vielleicht drei Bildschirmseiten füllt, steht einfach als eine Anweisung in einer Zeile. Das ist vor allem deshalb von Vorteil, weil man sich nur einmal mit den Details einer Funktion beschäftigen muss, nämlich dann, wenn man sie erstellt. Für die Nutzung im Programm will man diese Information gar nicht haben, sie stören hier nur (Informationsüberfluß). &lt;br /&gt;
* Leistungsfähigkeit: Ein gut modularisiertes Programm erreicht ein bestimmte Funktionalität einfach und kompakt, weil die einzelnen Funktionen so angelegt sind, dass sie einfach und dennoch vielfältig verwendet werden können. Wichtig ist dabei die richtige Portionierung.&lt;br /&gt;
**Welche Funktion sollen immer zusammen sein, welche sollten getrennt werden?&lt;br /&gt;
**Wie gestaltet man die Parameter für eine Funktion sinnvoll?&lt;br /&gt;
* Testbarkeit: Das leidige Thema der Softwareentwicklung ist der Test. Dieser sollte theoretisch alle Fehler finden, praktisch wird das aber oft nicht erreicht. Da Software meist eine recht komplexe Sache ist, kann man sie nur sehr schwer als Gesamtwerk vollständig prüfen. Darum müssen zuerst die Teile einzeln getestet werden. Ein gut modularisiertes Programm kann man leichter testen.&lt;br /&gt;
&lt;br /&gt;
== Beiträge im Forum ==&lt;br /&gt;
&lt;br /&gt;
*[http://www.mikrocontroller.net/topic/26550#new C++ CodeChecking (Style,...)]&lt;br /&gt;
*[http://www.mikrocontroller.net/topic/132304#new Tutorial für _sauberen_ C-Code]&lt;br /&gt;
*[[Erweiterte LCD-Ansteuerung]]: Artikel mit einem einfachen Beispiel für strukturierte Programmierung&lt;br /&gt;
&lt;br /&gt;
== Weblinks ==&lt;br /&gt;
&lt;br /&gt;
* [http://www.gimpel.com/html/pcl.htm PC-lint, ein Analyseprogramm für C-Code]&lt;br /&gt;
* [http://www.chris-lott.org/resources/cstyle/indhill-cstyle.html Recommended C Style and Coding Standards, engl.]&lt;br /&gt;
* [http://www.jetcafe.org/jim/c-style.html Standards and Style for Coding in ANSI C, engl.]&lt;br /&gt;
* [http://de.wikipedia.org/wiki/Programmierstil Wikipediaartikel über Programmierstil]&lt;br /&gt;
* [http://www.campwoodsw.com/sourcemonitor.html Tool zur statischen Codeanalyse u.a. für C/C++]&lt;br /&gt;
*[http://en.wikipedia.org/wiki/Program_optimization Program optimization] auf Wikipedia, engl.&lt;br /&gt;
* [https://sites.google.com/site/artcfox/demystifying-the-tlc5940 demystifying-the-tlc5940] Umfassende Erklärung zur Ansteuerung eines TLC5940 sowie Hinweisen zum Vorgehen bei der Einarbeitung in neue Hard- und Software, engl.&lt;br /&gt;
* [http://kotaku.com/5975610/the-exceptional-beauty-of-doom-3s-source-code The Exceptional Beauty of Doom 3&#039;s Source Code] (engl.)&lt;br /&gt;
* [ftp://ftp.idsoftware.com/idstuff/doom3/source/CodeStyleConventions.doc CodeStyleConventions.doc] von iD Software für DOOM 3 &lt;br /&gt;
* [http://www.amazon.de/Weniger-schlecht-programmieren-Kathrin-Passig/dp/3897215675/ref=sr_1_1?ie=UTF8&amp;amp;qid=1444238128&amp;amp;sr=8-1&amp;amp;keywords=weniger+schlecht+programmieren Weniger schlecht programmieren], ISBN: 3897215675&lt;br /&gt;
* [http://c2.com/cgi/wiki?ThreeStarProgrammer ThreeStarProgrammer]: Warum man keinen hochkomplexen Code schreiben soll (engl.)&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[Kategorie:Algorithmen und Arithmetik]]&lt;br /&gt;
[[Kategorie:Mikrocontroller]]&lt;/div&gt;</summary>
		<author><name>213.179.131.90</name></author>
	</entry>
	<entry>
		<id>https://www.mikrocontroller.net/index.php?title=Klangerzeugung&amp;diff=79645</id>
		<title>Klangerzeugung</title>
		<link rel="alternate" type="text/html" href="https://www.mikrocontroller.net/index.php?title=Klangerzeugung&amp;diff=79645"/>
		<updated>2013-11-20T10:08:11Z</updated>

		<summary type="html">&lt;p&gt;213.179.131.90: PIC zum AVR hinzugefügt&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;Die Methode zur Geräuscherzeugung hängt natürlich von der Hardware und dem gewünschten Ergebnis ab. Im einfachsten Fall macht ein Piezo-Element an einer Messingmembran Piepsgeräusche, aber auch Sprachwiedergabe über Lautsprecher ist möglich.&lt;br /&gt;
&lt;br /&gt;
== Erzeugung der Tonfrequenzen ==&lt;br /&gt;
&lt;br /&gt;
=== Sinustabelle ===&lt;br /&gt;
&lt;br /&gt;
Man kann im Flash eine Sinustabelle ablegen, die schneller oder langsamer abgetastet wird und so eine PWM ermöglicht. Schon hat man Sinustöne variabler Frequenz, die sehr schön rund klingen. Mit etwas Rechenaufwand kann man noch Lautstärke-Hüllkurven draufmodulieren (AM) und somit glockenähnliche Sounds erzeugen.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Weblinks&#039;&#039;&#039;&lt;br /&gt;
# [http://www.microsyl.com/index.php/2010/03/23/door-bell/ Doorbell] bei www.microsyl.com (en, AVR, C)&lt;br /&gt;
&lt;br /&gt;
=== Voltage controlled Oscillator (VCO) ===&lt;br /&gt;
&lt;br /&gt;
* XR8038 oder MAX038&lt;br /&gt;
* XR2206&lt;br /&gt;
&lt;br /&gt;
=== Spezielle Klang-ICs ===&lt;br /&gt;
&lt;br /&gt;
Für spezielle Klänge werden ICs angeboten z.B. &lt;br /&gt;
&lt;br /&gt;
Der klassische Gong-IC SAE800&lt;br /&gt;
-&amp;gt; Conrad, Reichelt, Bausatz bei ELV&lt;br /&gt;
Desweiteren:&lt;br /&gt;
* UM 3561 -&amp;gt; Conrad&lt;br /&gt;
* [http://www1.conrad.de/scripts/wgate/zcop_b2c/?~template=pcat_area&amp;amp;p_load_area=SHOP_AREA_17354&amp;amp;zhmmh_area_kz=13&amp;amp;navi=mitte Module bei Conrad]&lt;br /&gt;
&lt;br /&gt;
Mit Voice-Recorder lassen sich kurze Audiosequenzen über ein Mikrofon aufnehmen und auf Befehl abspielen.&lt;br /&gt;
* ISD25xx z.&amp;amp;nbsp;B. ISD2560 -&amp;gt; Reichelt&lt;br /&gt;
* ISD17xx z.&amp;amp;nbsp;B. ISD1730 -&amp;gt; ?&lt;br /&gt;
* ISD14xx z.&amp;amp;nbsp;B. ISD1416 -&amp;gt; Conrad&lt;br /&gt;
* [http://www.roboternetz.de/wissen/index.php/RN-Speak Beispiel] aus Roboternetz.de&lt;br /&gt;
&lt;br /&gt;
DTMF, Telefongetute&lt;br /&gt;
* MT 8880 -&amp;gt; Conrad&lt;br /&gt;
* MT 8870 -&amp;gt; Conrad&lt;br /&gt;
* CM 8870&lt;br /&gt;
&lt;br /&gt;
Der Klassiker aus dem C64&lt;br /&gt;
* MOS 6581/SID 6581 C64-Soundchip -&amp;gt; eBay&lt;br /&gt;
* [http://www.roboterclub-freiburg.de/atmega_sound/atmegaSID.html SID-Emulator] mit AVR&lt;br /&gt;
&lt;br /&gt;
== Digital-Analog-Wandlung ([[DAC]]) ==&lt;br /&gt;
&lt;br /&gt;
Die Wechselspannung für Verstärker, Lautsprecher und elektronikfreies Piezoelement kann vom µC auf verschiedene Weise erzeugt werden. &lt;br /&gt;
&lt;br /&gt;
Mit einem Kondensator in der Signalleitung kann ein eventuell vorhandener Gleichspannungsanteil (DC-Offset) entfernt werden.&lt;br /&gt;
&lt;br /&gt;
=== R2R-Netzwerk ===&lt;br /&gt;
Siehe [[Widerstandsnetzwerk]], [http://de.wikipedia.org/wiki/R2R-Netzwerk R2R-Netzwerk] Samplerate direkt in der Ausgabe&lt;br /&gt;
&lt;br /&gt;
* http://www.myplace.nu/avr/minidds/index.htm (Englisch)&lt;br /&gt;
&lt;br /&gt;
=== [[PWM]] ===&lt;br /&gt;
Für richtiges Audio:&lt;br /&gt;
schnell laufendes PWM&lt;br /&gt;
Der Controller schnell getaktet &lt;br /&gt;
je nach gewünschter Samplerate (Samplerate x 256)&lt;br /&gt;
&lt;br /&gt;
Wenn Piezo, dann PWM mit 50% Duty-Cycle. Die Toggle-Frequenz entspricht der halben Tonhöhe (zwei mal Umschalten pro Periode).&lt;br /&gt;
&lt;br /&gt;
Meistens liefert eine Direktbeschaltung der Ausgangsstufe an einem Mikrocontroller nicht genügend Leistung. Bereits eine einfache Treiberstufe kann Abhilfe schaffen.  &lt;br /&gt;
&lt;br /&gt;
[[Bild:Pwm-wandler.svg]]&lt;br /&gt;
&lt;br /&gt;
Die 20Ω Widerstand/ 4,7 µF Kondensator Kombination als [[Filter#Tiefpass|Tiefpass]] entfernt die hohen Frequenzen des [[Pulsweitenmodulation|PWM]]-Signals aus dem Audiosignal.&lt;br /&gt;
&lt;br /&gt;
Durch Verringern des Ausgangswiderstandes kann noch etwas mehr Leistung herausgeholt werden.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Weblinks&#039;&#039;&#039;&lt;br /&gt;
# [http://elm-chan.org/works/sd8p/report.html Simple SD Audio Player with ATtiny85] (elm-chan.org)&lt;br /&gt;
# [http://projectproto.blogspot.com/2010/05/pic18f-sd-wav-audio-player.html PIC18F SD WAV Audio Player] ähnlich 1 zusätzlich mit Tiefpassfilter&lt;br /&gt;
# [[AVR-Synthesizer]]&lt;br /&gt;
&lt;br /&gt;
== Hardware ==&lt;br /&gt;
&lt;br /&gt;
=== Piezo-Element ===&lt;br /&gt;
&lt;br /&gt;
Piezo-Elemente sind einfach anzusteuern und als Buzzer/Summer von Reichelt, Conrad... erhältlich.&lt;br /&gt;
&lt;br /&gt;
Es gibt hier zwei Typen:&lt;br /&gt;
* Mit integrierter Elektronik; braucht nur mit Gleichspannung versorgt zu werden. &lt;br /&gt;
* Ohne Elektronik; braucht eine Wechselspannung.&lt;br /&gt;
&lt;br /&gt;
Die Piezo-Elemente haben eine Eigenresonanzfrequenz um 1,5 kHz (&amp;quot;Fiep&amp;quot;), und sind damit am lautesten. Fertige Module sind oft mit Resonanzkörper ausgestattet ([http://de.wikipedia.org/wiki/Helmholtz-Resonator Helmholtz-Resonator]).&lt;br /&gt;
&lt;br /&gt;
Piezo Elemente ohne integrierte Elektronik können direkt an die Pins eines AVR oder PIC angeschlossen werden. Um die Lautstärke zu erhöhen, kann man zwei Pins benutzen, die immer abwechselnd auf LOW bzw. HIGH gesetzt werden. Dadurch ergibt sich eine Wechselspannung um V_cc. (Prinzip der H-Brücke)&lt;br /&gt;
&lt;br /&gt;
Bei selbsterregenden Elementen (die aus einer Gleichspannung ihre Frequenz selbst erzeugen) sollte man auf die Daten achten. Im Allgemeinen brauchen kleine Module aber auch nur einige mA.&lt;br /&gt;
&lt;br /&gt;
=== Lautsprecher ===&lt;br /&gt;
Um Lautsprecher an einem µC betreiben zu können, bedarf es in den meisten Fällen eines Verstärkers, da die Portpins des µC i.d.R. nur wenige mA Strom vertragen (Datenblatt!).&lt;br /&gt;
&lt;br /&gt;
== Weblinks ==&lt;br /&gt;
(TODO: Sichten und den verschiedenen Methoden zuordnen)&lt;br /&gt;
&lt;br /&gt;
* http://www.infolexikon.de/blog/atmega-music/ (de, AVR, C)&lt;br /&gt;
* http://elm-chan.org/works/mxb/report_e.html (en, AVR, ASM)&lt;br /&gt;
* http://www.microsyl.com/intercomm/intercomm.html (en, AVR, C)&lt;br /&gt;
* http://www.elby-designs.com/avrsynth/avrsyn-about.htm (en)&lt;br /&gt;
* http://www.mikrocontroller.net/topic/25051 (en,AVR,ASM)&lt;br /&gt;
* AVR314: DTMF Generator&lt;br /&gt;
* AVR335: Digital Sound Recorder with AVR and DataFlash&lt;br /&gt;
* AVR336: ADPCM Decoder&lt;br /&gt;
* http://www.avrfreaks.net/index.php?name=PNphpBB2&amp;amp;file=viewtopic&amp;amp;p=276201 (en, AVR)&lt;br /&gt;
* http://www.hanneslux.de/avr/divers/melody/index.html (de, ASM)&lt;br /&gt;
* http://www.jcwolfram.de/projekte/avr/avrmusicbox/main.php (de, ASM)&lt;br /&gt;
* [http://www.rpi.edu/~kouttd/03/Rage_against_the_arduino.html Rage Against The AVR] - WAV-Daten mit PWM über Atmega48 in Stereo ausgeben (en, BASCOM AVR, PC: Python)&lt;br /&gt;
* [http://hackaday.com/2009/09/29/make-an-arduino-talk-to-you/ Make an Arduino talk to you] auf hackaday.com&lt;br /&gt;
* [http://jeremyblum.com/2010/09/05/driving-5-speakers-simultaneously-with-an-arduino/ Driving 5 speakers simultaneously with an Arduino] by Jeremy Blum.&lt;br /&gt;
&lt;br /&gt;
* [http://www2.hsu-hh.de/ant/dafx2002/papers/DAFX02_Karjalainen_Valimaki_Esquef_bell-like_sounds.pdf Glocken-Ton erzeugen]&lt;br /&gt;
* Im mikrocontroller.net-Forum, Suchbegriffe z. B.&#039;&#039;Sound&#039;&#039; o.ä.&lt;br /&gt;
* [http://www.discovercircuits.com/S/soundsyn.htm discovercircuits.com], Umfangreiche Linksammlung&lt;br /&gt;
*[http://www.anthonymattox.com/arduino-synthesizer Arduino Synthesizer] (R2R+DAC)&lt;br /&gt;
*[http://roboterclub-freiburg.de/atmega_sound/atmegaSID.html C64 SID Emulation auf Atmega8 und Atmega168]&lt;br /&gt;
*[http://sourceforge.net/projects/atmegasid/files/ C64 SID mit I2C auf Sourceforge ]&lt;br /&gt;
* 1-Bit Sound:&lt;br /&gt;
** [[OneBitSound]]&lt;br /&gt;
** [http://web.media.mit.edu/~nvawter/projects/1bit/index.html The 1-Bit Groove Box] (Atmega32)&lt;br /&gt;
** [http://www.mikrocontroller.net/topic/135422 1-bit audio example program for Atmega] (Atmega32)&lt;br /&gt;
&lt;br /&gt;
[[Kategorie:Audio]]&lt;br /&gt;
[[Kategorie:Bauteile]]&lt;/div&gt;</summary>
		<author><name>213.179.131.90</name></author>
	</entry>
</feed>