Binärrechnen

Wie komme ich nun in einer originellen Umgebung auf die Frequenzen zur SID Programmierung, kann ich als Frage sehr leicht beantworten. Der Rechenprozess ist quasi mechanisch und grundlegend einfach, es wiederholen sich stetig dieselben Operationan, wobei ausgehend von dem einfachsten Wert die Ergebnisse immer größer und immer komplexer werden. Das Prinzip der geschichteten Quinten im Quintenzirkel und für die Diatonik ist ja bekannt. Ich nehme einen Ausgangswert, multipliziere ihn mit drei und bringe ihn anschließend durch Verdoppeln oder Halbieren in einen Wertebereich, der mir etwas nützt, für mich ist das vor allem die Mittlere Oktave.

Wie das mit gewohnten Zahlen funktioniert, haben wir in unserem Kulturkreis schon sehr früh in der Schule gelernt, für den Computer rechne ich hier mit Binärzahlen, um das Prinzip zu zeigen, die Ergebnisse werden zur Vereinfachung der Schreibweise beim Programmieren nicht dezimal verwendet sondern in Hexadezimalzahlen umgewandelt, das ist entsprechend der Menthalität einer solchen Maschine ein fast ebenso mechanischer Vorgang und vergleichsweise sehr viel einfacher.

Die Maschine kann im Grunde erstmal nur addieren, die benötigte Multiplikation 1*3 entspricht hier der Operation 1+1+1, das ist rein logisch und kein bisschen intelligent, die Logik einer Maschine folgt immer einem bestimmten, stark vereinfachten Muster, was wir so toll finden. Diese Addition entspricht hier einem logischen UND MIT ÜBERTRAG. Weil Binärzahlen, aus dem Statusunterschied zwischen High und Low, nur diese beiden Ziffern 0 und 1 haben, findet bei einer Operation 1+1 schon sofort der Übertrag in die nächsthöhere Stelle statt.

Der MOS6510 Prozessor beherrscht noch weitere logische Operationen, die sind hier aber erstmal uninteressant, wichtig zu bemerken ist, dass die Division und auch die Subtraktion nicht Teil der grundlegenden Maschinenlogik sind, dass also vor allem Werte vermehrt werden. Die Division und auch die Subtraktion sind natürlich am Computer, auch durch den MOS6510 Prozessor irgendwie möglich, dafür ist es aber schon nötig die Trickkiste aufzumachen, und verbreitete Prozessoren haben selbstverständlich Werkzeuge dieser Trickkiste schon fest implementiert, soweit sie ja ständig gebraucht werden.

Einer dieser einfachsten Tricks ist der Bitshift. Der Bitshift verdoppelt den Ausgangswert auf sehr einfache Weise, er verschiebt die gesamte Binärzahl um eine Stelle nach oben. Ebenso könnte ein Prozessor auch Werte halbieren, so würde sich alles um eine Stelle nach unten verschieben, das wiederspricht aber grundsätzlich schonwieder der einfachen Menthalität der Maschine durch Addition Werte zu „akkumulieren“ also zu vermehren, demnach ist das schonwieder eine etwas widerstrebende Operation, obwohl sie dem Menschen intuitiv erscheint. Der Bitshift ergibt sich ja schon aus der ersten Grundoperation UND MIT ÜBERTRAG 1+1=10 diese erste Grundoperation ist gleichzeitig ein Verdoppeln, wie jedes Kind sofort begreifen würde, also folgt daraus logisch, dass ein gesamter Übertrag aller vorhandenen Stellen den Ausgangswert verdoppelt.

Wow.. das genügt schon erstmal für unsere Diatonik, die beiden ersten Grundoperationen aus dem Wesen der Maschine Addition und Übertrag multiplizieren den Ausgangswert mit drei. Um den Rest, das Verschieben der Werte in den Bereich der Mittleren Oktave am SID kümmere ich mich später, ich darf hier nicht ein einziges Bit außer Acht lassen, also auch nicht aus dem Wertebereich der gesuchten Ergebnisse herausschieben, bevor ich mindestens alle benötigten Quinten „geschichtet“ habe. Die Binärzahl wächst dabei stetig an.

Ich gehe nach dem Wesen der Diatonik vom Wert 1 aus, und verdopple ihn erst durch Bitshift, danach Addiere ich den Ausgangswert, das entspricht der dreifachen Addition oder der Multiplikation mit drei auf dem denkbar einfachsten und schnellsten Weg. Diesen Prozess setze ich mit dem Ergebnis fort, ich akkumuliere :)

So funktioniert im menschlichen Geiste die logische Addition als Und mit Übertrag:

0+0=0

1+0=1

0+1=1

1+1=0 mitÜbertrag=10

0+0+Übertrag=1

0+1+Übertrag=0 mitÜbertrag=10

1+0+Übertrag=0 mitÜbertrag=10

1+1+Übertrag=1 mitÜbertrag=11

========

und im Takt von links nach rechts, zu lesen von rechts nach links, wie eine Maschine denken..

  1. 1
  2. 01 geshiftet
  3. 11 addiert
  4. 011 geshiftet
  5. 1001 addiert
  6. 01001 geshiftet
  7. 11011 addiert
  8. 011011 ..
  9. 1000101 .. Quinte
  10. 01000101 ..
  11. 11001111 Quinte
  12. 011001111
  13. 1001101101 Quinte
  14. 01001101101
  15. 110100010001 Quinte
  16. 0110100010001
  17. 1000010110011 ..
  18. 01000010110011
  19. 110001110011001 ..
  20. 0110001110011001
  21. 1001010101100111 ..
  22. 01001010101100111
  23. 110111111100110101
  24. ..

Ich brech das an dieser Stelle mal ab, damit es nicht zu unübersichtlich wird. Es ist ja inzwischen bekannt, wir benötigen 54 Tonstufen, die Maschine wird diese Operation also über hundertmal wiederholen, braucht dafür aber nur den Bruchteil einer Sekunde und wird keine Flüchtigkeitsfehler machen. Ich rechne hier schon seit gut einer Minute und verfalle schon nach dem dritten Schritt in Routine. Nach wievielen solcher Rechenschritte hat ein Mensch die Maschine wirklich verstanden? Ich kann es nicht sagen, und möchte wieder ein bisschen menschlich werden.

Die Frequenzen sollen am Ende 16 Stellige Binärzahlen sein, wobei die einzelnen Bit beim SID folgende Frequenzwerte haben:

LowByte

========

Bit0 = 1/16

Bit1 = 1/8

Bit2 = 1/4

Bit3 = 1/2

Bit4 = 1

Bit5 = 2

Bit6 = 4

Bit7 = 8

HighByte

========

Bit0 = 16

Bit1 = 32

Bit2 = 64

Bit3 = 128

Bit4 = 256

Bit5 = 512

Bit6 = 1024

Bit7 = 2048

Der Frequenzbereich geht also von 0Hz bis 4kHz in kleinsten Schritten von 1/16Hz.

Um jetzt nach bitgenauer Rechnung haufenweise geschichteter Quinten jedes Ergebnis ordentlich in die Mittlere Oktave zu bringen, verschiebe ich die Werte so, dass die erste Stelle mit einer 1 in Bit4 des HighByte steht, so sind alle Werte dann größer als 256 und kleiner als 512.

  • 0001 0000 / 0000 0000
  • 0001 1000 / 0000 0000
  • 0001 0010 / 0000 0000
  • 0001 1011 / 0000 0000
  • 0001 0001 / 0100 0000
  • 0001 1001 / 1110 0000
  • 0001 0011 / 0110 1000

Ok, das Prinzip ist klar. Ich kürz das mal hier ab, irgendwann fallen Stellen hinten raus, die können einfach ignoriert werden, die Quinen sind alle Berechnet, ein Fehler kann sich jetzt nichtmehr fortsetzen, und alle Werte kleiner als 1/16 spielen hier keine Rolle mehr. Ich werde sogar noch alle Bit um unteren Nibble des LowByte auf Null setzen, um hier als Ausgangswerte nur Ganze Zahlen zu haben, damit auch beim Verschieben in andere Oktaven kein Fehler durch Rausfallen eines Bit entstehen kann. Die Frequenzen aller darstellbaren Oktaven sind also auch rein logisch vollständig konsonant. Was dann tatsächlich der SID ausgibt, und was am Ende als physikalisch messbarer Klang den Lautsprecher verlässt und sich im Raum ausbreitet, das können diese Binärzahlen nicht vollständig verraten.