summaryrefslogtreecommitdiff
path: root/Dokumentation/doc.tex
blob: 56fc2f0f47429bbf59723f50dd982c00ef107940 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
\documentclass[12pt,a4paper]{scrartcl}
\usepackage[utf8]{inputenc}
\usepackage[ngerman]{babel}
\usepackage{graphicx}
\usepackage{amsmath,amssymb,amsfonts}
\usepackage[table,dvipsnames]{xcolor}
\usepackage{array}
\usepackage{makecell}

\definecolor{tablehead}{hsb}{0,0,0.9}
\newcolumntype{C}[1]{>{\centering\arraybackslash}p{#1}}

\title{Pinlock: Dokumentation}
\subtitle{Mikrocontroller-Seminar}
\author{Leonard Kugis, Mattes Melius}

\begin{document}

\maketitle

\tableofcontents

\newpage

\section{Idee}

\section{Hardware}

\subsection{Platinenaufbau}

\subsection{Mikrocontroller ATmega16A}

\subsection{Sonstige Komponenten}

\section{Software}

Das Programm wurde in AVR-Assembler geschrieben, mit Assemblerdirektiven
für den \emph{Avra}-Assembler.
Grundsätzlich wurden für dieses Programm die in Tabelle~\ref{tbl:registermap}
Register-Neudefinitionen vorgenommen, um den Code lesbarer zu gestalten.

\begin{table}[!htb]
  \centering
  \begin{tabular}{|C{0.2\linewidth}|C{0.2\linewidth}|C{0.5\linewidth}|}
    \hline
    \rowcolor{tablehead} ATmega16A Register & Neu definierte Registerbezeichnung & Funktion \\ \hline
    \texttt{r16} & \texttt{tmp0} & Temporäres Pufferregister 0 \\ \hline
    \texttt{r17} & \texttt{par0} & Parameterregister 0 \\ \hline
    \texttt{r18} & \texttt{par1} & Parameterregister 1 \\ \hline
    \texttt{r19} & \texttt{tmp1} & Temporäres Pufferregister 1 \\ \hline
    \texttt{r20} & \texttt{tmp2} & Temporäres Pufferregister 2 \\ \hline
    \texttt{r21} & \texttt{ret0} & Rückgaberegister 0 \\ \hline
    \texttt{r22} & \texttt{ret1} & Rückgaberegister 1 \\ \hline
    \texttt{r23} & \texttt{par2} & Parameterregister 2 \\ \hline
    \texttt{r24} & \texttt{par3} & Parameterregister 3 \\ \hline
    \texttt{r25} & \texttt{par4} & Parameterregister 4 \\ \hline
    \texttt{r26} & \texttt{ret2} & Rückgaberegister 2 \\ \hline
    \texttt{r27} & \texttt{heart} & Debug \\ \hline
    \texttt{r28} & \texttt{dig0} & Pufferregister für Ziffern 0 und 1 \\ \hline
    \texttt{r29} & \texttt{dig1} & Pufferregister für Ziffern 2 und 3 \\ \hline
  \end{tabular}
  \caption{Neu definierte Registerbezeichnungen für Register des ATmega16A}
  \label{tbl:registermap}
\end{table}

\subsection{Grundprinzip}

Nach Zurücksetzen des Mikrocontrollers durchläuft das Programm eine Initialisierungsroutine.
Diese beinhaltet im Wesentlichen folgende Schritte:

\begin{enumerate}
  \item Initialisierung des Stackpointers mit den Grenzen des verfügbaren RAMs
  \item Konfiguration der GPIO-Ports
  \item Initialisierung der Displays
  \item Lesen des Zugangscodes aus dem EEPROM
\end{enumerate}

Anschließend wird eine endlose Hauptschleife durchlaufen, die folgende Aktionen
periodisch ausführt:

\begin{enumerate}
  \item Warte 12240 Zyklen.
  \item Lese alle Tasten der Eingabematrix aus.
  \item Ermittle Änderungen des neuen Tastenstatus zu dem alten Tastenstatus.
  \item Bei positiver Flanke (Taste war vorher nicht gedrückt und ist jetzt gedrückt):
    Behandle den Tastendruck bezüglich des aktuellen Zustands (s.u.).
  \item Puffere den neuen Tastenstatus.
\end{enumerate}

Die einzelnen Routinen, die dabei aufgerufen werden, werden genauer in Sektion~\ref{sec:functions} erläutert.

Die Behandlung der (neu) gedrückten Taste bezüglich des aktuellen Zustandes erfolgt nach der
in Abbildung~\ref{fig:states} dargestellten \emph{Finite-State-Machine} (FSM).
Die Zustände sind dabei nach folgendem Schema benannt:

\begin{tabular}{r@{: }l r@{: }l}
  \texttt{A} & \emph{Authenticating}, Authentifizierung findet gerade durch Codeeingabe statt \\
  \texttt{AS} & \emph{Authentication Submitted}, Code wurde bestätigt und wird überprüft \\
  \texttt{AD} & \emph{Authenticated}, Benutzer ist authentifiziert und hat Zugriff \\
  \texttt{C} & \emph{Change}, Benutzer ändert den Zugriffscode
\end{tabular}

Dabei folgt die Notation der Transitionsbedingungen dem Schema \\
\colorbox{lightgray}{\texttt{<Taste> / <Wesentliche Aktionen>}}.
Die Tastendarstellungen innerhalb des Programmes unterliegen dabei der Zuordnung in
Tabelle~\ref{tbl:keymap}.

\begin{figure}[!htb]
  \centering
  \includegraphics[width=0.7\linewidth, keepaspectratio]{resources/states}
  \caption{FSM der Behandlung von Tastendrücken (schematisch)}
  \label{fig:states}
\end{figure}

\begin{table}[!htb]
  \centering
  \begin{tabular}{|c|c|}
    \hline
    \rowcolor{tablehead} Taste extern & Taste intern \\ \hline
    \texttt{0..9} & \texttt{0x00..0x09} \\ \hline
    \texttt{A..D} & \texttt{0x0A..0x0D} \\ \hline
    \texttt{*} & \texttt{0x0E} \\ \hline
    \texttt{\#} & \texttt{0x0F} \\ \hline
  \end{tabular}
  \caption{Zuordnung von externen zu internen Tastendarstellungen}
  \label{tbl:keymap}
\end{table}

\subsection{Routinen}\label{sec:functions}

\subsubsection{\texttt{wait}}

\begin{tabular}{r@{: }l r@{: }l}
  Parameter & \makecell[l]{\texttt{par0}: Wartezyklen Stufe 1, \\ \texttt{par1}: Wartezyklen Stufe 2, \\ \texttt{par2}: Wartezyklen Stufe 3} \\
  Rückgabe & -
\end{tabular}

Warte über drei verschachtelte Schleifen mit verschiedenen Durchlaufzahlen.
Die gesamte, zu wartende Zyklendauer beträgt somit
$\Delta t_\text{ges} = \text{\texttt{par0}} \cdot \text{\texttt{par1}} \cdot \text{\texttt{par2}}$.

\subsubsection{\texttt{write\_code}}

\begin{tabular}{r@{: }l r@{: }l}
  Parameter & - \\
  Rückgabe & -
\end{tabular}

Schreibe statisch die Werte 0x01 und 0x23 (entspricht der Zahlenkombination \texttt{0123})
in das EEPROM an die Adressen 0x00 und 0x01.

\subsubsection{\texttt{load\_code}}

\begin{tabular}{r@{: }l r@{: }l}
  Parameter & - \\
  Rückgabe & \makecell[l]{\texttt{ret0}: Ziffern 0 und 1, \\ \texttt{ret1}: Ziffern 2 und 3}
\end{tabular}

Lese die gespeicherte Zahlenkombination aus dem EEPROM (Adressen 0x00 und 0x01) aus.

\subsubsection{\texttt{shift\_out}}

\begin{tabular}{r@{: }l r@{: }l}
  Parameter & \makecell[l]{\texttt{par0}: Zu schreibendes Byte, \\
    \texttt{par1..par2}: Adresse zur Funktion, um 0 zu schreiben, \\
    \texttt{par3..par4}: Adresse zur Funktion, um 1 zu schreiben} \\
  Rückgabe & -
\end{tabular}

Schreibe ein Byte Bit für Bit durch Funktionsaufrufe, welche das Schreiben
des 0- und 1-Bits implementieren. Das können beispielsweise Funktionen sein,
die 0 bzw. 1 an ein Schieberegister anlegen.

\subsubsection{\texttt{shift\_in}}

\begin{tabular}{r@{: }l r@{: }l}
  Parameter & \makecell[l]{\texttt{par0..par1}: Adresse zur Funktion, um einen Clockzyklus zu durchlaufen, \\
    \texttt{par2..par3}: Adresse zur Funktion, das zugehörige Bit zu lesen} \\
  Rückgabe & \makecell[l]{\texttt{ret0}: Gelesenes Byte}
\end{tabular}

Lese ein Byte Bit für Bit aus einem Schieberegister. Das Durchlaufen eines Clockzyklus und Lesen des
Bits ist in übergebenen Funktionen implementiert.

\subsubsection{\texttt{eeprom\_write}}

\begin{tabular}{r@{: }l r@{: }l}
  Parameter & \makecell[l]{\texttt{par0..par1}: Zieladresse, \\
    \texttt{par2}: Zu schreibender Wert} \\
  Rückgabe & -
\end{tabular}

Schreibt ein Byte an die gegebene Adresse in das interne EEPROM.

\subsubsection{\texttt{eeprom\_read}}

\begin{tabular}{r@{: }l r@{: }l}
  Parameter & \makecell[l]{\texttt{par0..par1}: Adresse} \\
  Rückgabe & \makecell[l]{\texttt{ret0}: Gelesener Wert}
\end{tabular}

Liest ein Byte von der gegebenen Adresse im internen EEPROM.

\subsubsection{\texttt{status}}

\begin{tabular}{r@{: }l r@{: }l}
  Parameter & \makecell[l]{\texttt{par0}: Statusbits} \\
  Rückgabe & -
\end{tabular}

Gibt die gegebenen Statusbits über die LEDs aus.
Dabei wird das Schieberegister dafür benutzt.

\subsubsection{\texttt{display}}

\begin{tabular}{r@{: }l r@{: }l}
  Parameter & \makecell[l]{\texttt{par0}: Displaynummer, \\ \texttt{par1}: Darzustellende Ziffer} \\
  Rückgabe & -
\end{tabular}

Zeige die gegebene Ziffer auf dem gegebenen Display.

\subsubsection{\texttt{set\_digit}}

\begin{tabular}{r@{: }l r@{: }l}
  Parameter & \makecell[l]{\texttt{par0}: Ziffernstelle, \\ \texttt{par1}: Ziffer} \\
  Rückgabe & -
\end{tabular}

Schreibt die Ziffer an die Ziffernstelle des internen Puffers.

\subsubsection{\texttt{get\_digit}}

\begin{tabular}{r@{: }l r@{: }l}
  Parameter & \makecell[l]{\texttt{par0}: Ziffernstelle} \\
  Rückgabe & \makecell[l]{\texttt{ret0}: Ziffer an der Stelle}
\end{tabular}

Liest die Ziffer der gegebenen Stelle von dem internen Puffer.

\subsubsection{\texttt{input}}

\begin{tabular}{r@{: }l r@{: }l}
  Parameter & - \\
  Rückgabe & \makecell[l]{\texttt{ret0}: Tastenstatus mit Belegung: \texttt{0852*741}, \\
    \texttt{ret1}: Tastenstatus mit Belegung: \texttt{DCBA\#963}}
\end{tabular}

Liest den Tastenstatus aller Tasten aus. Ein 1-Bit entspricht einer gedrückten,
ein 0-Bit einer nicht gedrückten Taste.
Das Auslesen der Tasten der Eingabematrix erfolgt über die Schieberegister:
eines (Serial-In-Parallel-Out) zur Selektion der auszulesenden Zeile und eines (Parallel-In-Serial-Out)
zum eigentlichen Auslesen selbiger. Dies wird innerhalb der Ausleseroutine mit jeder
Zeile gemacht, um gedrückte Tasten zu identifizieren.

\subsubsection{\texttt{translate}}

\begin{tabular}{r@{: }l r@{: }l}
  Parameter & \makecell[l]{\texttt{par0}: Tastenstatus Bits \texttt{7..0}, \\
    \texttt{par1}: Tastenstatus Bits \texttt{15..8}} \\
  Rückgabe & \makecell[l]{\texttt{ret0}: Übersetzter Tastencode}
\end{tabular}

Übersetzt den Tastenstatus in die entsprechende, interne Tastendarstellung.
Dabei wird nach der Zuordnung aus Tabelle~\ref{tbl:keymap} vorgegangen.

\subsubsection{\texttt{handle}}

\begin{tabular}{r@{: }l r@{: }l}
  Parameter & \makecell[l]{\texttt{par0}: Aktueller Zustand, \\
    \texttt{par1}: Tastencode} \\
  Rückgabe & \makecell[l]{\texttt{ret0}: Neuer Zustand}
\end{tabular}

Behandle den Tastencode unter dem aktuellen Zustand.
Das Zustandsfeld hat folgende Belegung (ein Zeichen entspricht einem Bit):

\begin{center}
  \texttt{CSSSSSDD}
\end{center}

\begin{tabular}{r@{: }l r@{: }l}
  \texttt{0} & Reserviert \\
  \texttt{C} & Pufferbit für Blinken der ausgewählten Stelle \\
  \texttt{S} & Zustandsinformationen \\
  \texttt{D} & Aktuell ausgewähltes Display
\end{tabular}

Die Behandlung erfolgt nach dem in Abbildung~\ref{fig:states} dargestellten Schema.

\section{Bedienung}

Nach Zurücksetzen des Systems ist man in der Authentifizierungsphase.
In dieser ist die richtige Ziffernkombination einzugeben, welcher vorher gespeichert wurde.
Der Standardcode ist \texttt{0123}.
Es stehen dabei folgende Optionen zur Auswahl:

\begin{tabular}{r@{: }l r@{: }l}
  \texttt{0..9} & Ziffer eingeben \\
  \texttt{A} & Eingabe bestätigen \\
  \texttt{*} & Zeigerposition nach links schieben \\
  \texttt{\#} & Zeigerposition nach rechts schieben
\end{tabular}

Wurde die falsche Ziffernkombination eingegeben und bestätigt,
erlischen alle Displays für wenige Sekunden und es ist eine erneute Eingabe möglich. \\
Wurde die richtige Ziffernkombination eingegeben und bestätigt, wird dies mit
setzen aller Displays auf 0 und erlischen des Zeigers angezeigt.
Man ist nun authentifiziert, was einem Zugriff auf das System darstellt.
In diesem Zustand stehen folgende Funktionen zur Auswahl:

\begin{tabular}{r@{: }l r@{: }l}
  \texttt{B} & Ändern des Zugangscodes \\
  \texttt{D} & Ausloggen
\end{tabular}

Der Zugangscode lässt sich nach Drücken von \texttt{B} mit der selben Steuerung
wie bei der Zifferneingabe in der Authentifizierungsphase ändern, wobei
\texttt{A} dem Bestätigen der Änderung entspricht. Dabei wird der Zugangscode
in den persistenten Speicher geschrieben und in zukünftigen Authentifizierungsphasen
abgefragt. \\
Durch Ausloggen wird der authentifizierte Zustand verlassen und man ist wieder in
der Authentifizierungsphase.

\end{document}