Apostolos Fanakis
4 years ago
101 changed files with 6201 additions and 0 deletions
@ -0,0 +1,5 @@ |
|||
\section{Εισαγωγή} |
|||
|
|||
Το παρόν έγγραφο είναι η αναφορά του δεύτερου εργαστηρίου στο μάθημα Μικροεπεξεργαστές και Περιφερειακά. Στο δεύτερο εργαστήριο μας δόθηκε κώδικας που συνδυάζει τον simulator του εργαλείου Keil με το εργαλείο redBlocks στο οποίο έγινε προσομοίωση των φυσικών στοιχείων (οθόνη, leds, διακόπτες κλπ.). Ο κώδικας αφορούσε τη λειτουργία ενός αυτόματου πωλητή (vending machine). Μας ζητήθηκε να τροποποιήσουμε κώδικα ώστε να προσθέσουμε δύο λειτουργικότητες, την προσθήκη ενός κουμπιού με το πάτημα του οποίου εκκινείται η λειτουργία του πωλητή και τον υπολογισμό των ρέστων που θα πρέπει να πάρει ο χρήστης στο τέλος της αγοράς. Με τον συνδυασμό των εργαλείων είναι δυνατή η προσομοίωση και ο έλεγχος του project συνολικά. |
|||
|
|||
Ο κώδικας είναι διαθέσιμος στα συνημμένα καθώς και στο Gitlab repository \href{https://gitlab.com/apostolof-ece-auth-gr/microprocessors-and-peripherals-2021}{εδώ}. |
@ -0,0 +1,27 @@ |
|||
\section{Υλοποίηση} |
|||
|
|||
Αρχικά τροποποιήθηκε το project στο εργαλείο redBlocks, όπου με χρήση του γραφικού περιβάλλοντος έγινε προσθήκη ενός νέου κουμπιού START. Για την επίτευξη αυτού δημιουργήθηκε αρχικά ένα νέο digital input interface και έπειτα έγινε χρήση του interface σε ένα νέο view component. |
|||
|
|||
Τα μέρη του κώδικα που τροποποιήθηκαν είναι: |
|||
|
|||
\begin{itemize} |
|||
|
|||
\item το header file \inlcode{LowLevelPlatform.h} |
|||
\item το header file \inlcode{PlatformCallbacks.h} |
|||
\item το source file \inlcode{Application.cpp} |
|||
\item το source file \inlcode{main.cpp} |
|||
\item το source file \inlcode{VendingMode.cpp} |
|||
\end{itemize} |
|||
|
|||
Αρχικά, στο header \inlcode{LowLevelPlatform.h} προστέθηκε ένα νέο type definition για το κουμπί \inlcode{StartButton}. Έπειτα, στο ίδιο αρχείο, το \inlcode{StartButton} προστέθηκε στη λίστα των digital inputs ενώ έγινε ρύθμιση για trigger με θετική αιχμή. |
|||
|
|||
Στο αρχείο \inlcode{PlatformCallbacks.h} προστέθηκε ο ορισμός μία \inlcode{extern “C”} συνάρτησης με όνομα \inlcode{onStartPressed}. Ο ορισμός αυτό χρησιμοποιήθηκε ως callback για το κουμπί \inlcode{StartButton}. |
|||
|
|||
Στο αρχείο \inlcode{Application.cpp} προστέθηκε η γραμμή \inlcode{Platform::StartButton::enableCallback()} με σκοπό την ενεργοποίηση του callback που ορίσαμε στο αρχείο \inlcode{PlatformCallbacks.h}. |
|||
|
|||
Η υλοποίηση της συνάρτησης \inlcode{onStartPressed} έγινε στο αρχείο \inlcode{main.cpp}. H callback αυτή είναι πολύ απλή και αλλάζει μία global boolean μεταβλητή με όνομα \inlcode{should\_continue} σε true. |
|||
|
|||
Άλλες τροποποιήσεις που έγιναν στο αρχείο είναι η προσθήκη ενός βρόχου μέσα στη main ο οποίος καλεί τη \inlcode{\_\_WFI} (wait for interrupt). Ο βρόχος έχει τοποθετηθεί πριν το run του application και γίνεται έξοδος μόνο όταν η μεταβλητή \inlcode{should\_continue} γίνει true. Έτσι το πρόγραμμα ξεκινά μόνο αφού πατηθεί το κουμπί start. Τέλος, στο αρχείο αυτό προστέθηκε επίσης η συνάρτηση \inlcode{getChange} η οποία δέχεται ως ορίσματα τα χρήματα που έχει δώσει ο χρήστης και την τιμή του αντικειμένου που επέλεξε, ώστε να υπολογίσει τα ρέστα τα οποία τυπώνει στο debug log. |
|||
|
|||
Στο source file \inlcode{VendingMode.cpp} έγινε χρήση της \inlcode{getChange} στα κατάλληλα σημεία ώστε να γίνει ο υπολογισμός των ρέστων. Τα σημεία αυτά, είναι η συνάρτηση \inlcode{onCoinsInserted} και συγκεκριμένα στην περίπτωση που ο χρήστης έχει ήδη επιλέξει ποτό και η συνάρτηση \\ \inlcode{onProductButtonPressedEvent} όταν ο χρήστης έχει ήδη εισάγει χρήματα. |
|||
|
@ -0,0 +1,7 @@ |
|||
\section{Προβλήματα που αντιμετωπίστηκαν} |
|||
|
|||
Κύριο πρόβλημα που αντιμετωπίσαμε ήταν ότι δεν ήμασταν σίγουροι που πρέπει να καλέσουμε τις συναρτήσεις μας, καθώς μας ζητήθηκε να μην επέμβουμε στον κώδικα c++ (είχαμε κάνει μια αρχική υλοποίηση σε c++, αλλά την αλλάξαμε). Για το λόγο αυτό βάλαμε την \inlcode{onStartPressed} μέσα στη main πριν την εντολή \inlcode{app.run()} όπου ξεκινάει και η λειτουργία του μηχανήματος. Την \inlcode{getChange} όμως την καλούμε μέσα στο \inlcode{VendingMode.cpp} πριν γίνει η κλήση της συνάρτησης \inlcode{startReleaseWorkflow()}, δηλαδή πριν το μηχάνημα ελευθερώσει το αντίστοιχο προϊόν. Δε βρήκαμε πως να την καλούμε αλλιώς, ώστε να μην επέμβουμε καθόλου στον κώδικα c++ και να παίρνουμε και τις τιμές για κόστος προϊόντος και χρήματα που έχουν μπει. |
|||
|
|||
Ένα μικρό πρόβλημα που είχαμε στην αρχή, ήταν ότι δεν είχαμε προσθέσει τον κατάλληλο κώδικα στο αρχείο \inlcode{Application.cpp} με αποτέλεσμα να μη λειτουργεί το κουμπί μας. |
|||
|
|||
Αρχικά είχαμε κάνει υλοποίηση με τροποποίηση του κώδικα c++ με αλλαγές στο \inlcode{VendingMode}, κατάλληλα \inlcode{VendingScreen}, όμως όπως μας απαντήσατε και στο e-mail δεν ήταν αυτό που θέλατε, οπότε σπεύσαμε την παραμονή του εργαστηρίου να υλοποιήσουμε την άσκηση εκ νέου. |
@ -0,0 +1,3 @@ |
|||
\section{Δοκιμές (testing)} |
|||
|
|||
Για τον έλεγχο της υλοποίησης έγινε δοκιμή του κώδικα χρησιμοποιώντας τον συνδυασμό των δύο εργαλείων προσομοίωσης και ακολουθώντας τις διάφορες πιθανές ροές χρήσης του μηχανήματος. Για παράδειγμα, πάτημα οποιουδήποτε άλλου κουμπιού πέραν του START στο ξεκίνημα - το μηχάνημα δεν κάνει τίποτα. Επιλογή προϊόντος και στη συνέχεια εισαγωγή χρημάτων ή και το ανάποδο - τυπώνονται στα ρέστα στο debug log και το μηχάνημα ελευθερώνει το προϊόν. |
@ -0,0 +1,52 @@ |
|||
% Heavily based on this template: |
|||
% https://www.overleaf.com/latex/templates/university-of-lincoln-computer-science-thesis-template-unofficial/vdbphtsnwdqv |
|||
|
|||
% Define variables |
|||
\makeatletter |
|||
|
|||
\newcommand{\universityLogo}[1]{\def\@logo{#1}} |
|||
\newcommand{\programme}[1]{\def\@programmename{#1}} |
|||
\newcommand{\school}[1]{\def\@schoolname{#1}} |
|||
\newcommand{\university}[1]{\def\@universityname{#1}} |
|||
\newcommand{\workshopTeamNumber}[1]{\def\@workshopteamnumber{#1}} |
|||
\newcommand{\semester}[1]{\def\@semester{#1}} |
|||
|
|||
\makeatother |
|||
|
|||
% Change the author concat text |
|||
\renewcommand*{\Authand}{ και } |
|||
|
|||
% Make custom title |
|||
\makeatletter |
|||
\renewcommand\maketitle{ |
|||
{\raggedright |
|||
\begin{center} |
|||
|
|||
% Make the title |
|||
{\huge \@title} |
|||
\vspace{0.5cm} |
|||
|
|||
% The authors, school and university name |
|||
{\@semester \\ |
|||
\@programmename \\ |
|||
\@schoolname \\ |
|||
\@universityname} |
|||
|
|||
% Print the team |
|||
\vspace{0.5cm} |
|||
{\Large Ομάδα \@workshopteamnumber} |
|||
|
|||
% The authors |
|||
{\Large \@author} |
|||
|
|||
% Then the date |
|||
\vspace{0.5cm} |
|||
{\footnotesize \@date} |
|||
|
|||
\end{center}} |
|||
} |
|||
\makeatother |
|||
|
|||
% Inline code command |
|||
|
|||
\newcommand{\inlcode}[1]{\colorbox{codebackground}{\footnotesize\texttt{#1}}} |
@ -0,0 +1,6 @@ |
|||
\usepackage{fontspec} |
|||
\usepackage[nonumeralsign]{xgreek} |
|||
\usepackage{hyperref} |
|||
\usepackage{authblk} |
|||
\usepackage{xcolor} |
|||
\usepackage{listings} |
@ -0,0 +1,14 @@ |
|||
\title{Μικροεπεξεργαστές και Περιφερειακά} |
|||
\programme{Τμήμα Ηλεκτρολόγων Μηχανικών και Μηχανικών Υπολογιστών} |
|||
\school{Πολυτεχνική Σχολή} |
|||
\university{Αριστοτέλειο Πανεπιστήμιο Θεσσαλονίκης} |
|||
\workshopTeamNumber{25} |
|||
\semester{8\textsuperscript{ο} εξάμηνο} |
|||
|
|||
\author[1]{Πιπινιάς Ιωάννης} |
|||
\author[2]{Φανάκης Απόστολος} |
|||
|
|||
\affil[1]{\textit{7965, \href{mailto:pipinias@ece.auth.gr}{pipinias@ece.auth.gr}}} |
|||
\affil[2]{\textit{8261, \href{mailto:apostolof@ece.auth.gr}{apostolof@ece.auth.gr}}} |
|||
|
|||
\date{\today} |
Binary file not shown.
@ -0,0 +1,32 @@ |
|||
\documentclass[11pt]{article} |
|||
\usepackage{geometry} |
|||
\geometry{a4paper, top=2.5cm, bottom=2.5cm, left=2.2cm, right=2.2cm} |
|||
|
|||
% Pcakges used |
|||
\input{packages} |
|||
|
|||
% Custom styles |
|||
\input{styling} |
|||
|
|||
% Custom commands |
|||
\input{custom-commands/custom-title} |
|||
|
|||
% Cover page details |
|||
\input{report-details} |
|||
|
|||
% start of report body |
|||
% --------------------------- |
|||
|
|||
\begin{document} |
|||
|
|||
\maketitle |
|||
|
|||
\input{chapters/1.0.introduction.tex} |
|||
\input{chapters/2.0.implementation.tex} |
|||
\input{chapters/3.0.issues-faced.tex} |
|||
\input{chapters/4.0.testing.tex} |
|||
|
|||
\end{document} |
|||
|
|||
% end of report body |
|||
% -------------------------- |
@ -0,0 +1,29 @@ |
|||
% Fonts |
|||
% \setmainfont{Linux Libertine O} |
|||
\setmainfont{GFS Didot} |
|||
|
|||
% Code styling |
|||
\definecolor{codebackground}{RGB}{240, 240, 240} |
|||
|
|||
\lstdefinestyle{codestyle}{ |
|||
backgroundcolor=\color{codebackground}, |
|||
basicstyle=\ttfamily\footnotesize, |
|||
breakatwhitespace=false, |
|||
breaklines=true, |
|||
captionpos=b, |
|||
keepspaces=true, |
|||
numbers=left, |
|||
numbersep=5pt, |
|||
showspaces=false, |
|||
showstringspaces=false, |
|||
showtabs=false, |
|||
tabsize=2 |
|||
} |
|||
|
|||
\lstset{style=codestyle} |
|||
|
|||
% Other styles |
|||
\setlength{\parskip}{0.2cm} |
|||
|
|||
\hypersetup{colorlinks=true, linkcolor=black, urlcolor=blue, citecolor=blue} |
|||
\urlstyle{same} |
@ -0,0 +1,89 @@ |
|||
<?xml version="1.0" encoding="UTF-8" standalone="no"?> |
|||
<?fileVersion 4.0.0?><cproject storage_type_id="org.eclipse.cdt.core.XmlProjectDescriptionStorage"> |
|||
<storageModule moduleId="org.eclipse.cdt.core.settings"> |
|||
<cconfiguration id="cdt.managedbuild.toolchain.gnu.cygwin.base.957472714"> |
|||
<storageModule buildSystemId="org.eclipse.cdt.managedbuilder.core.configurationDataProvider" id="cdt.managedbuild.toolchain.gnu.cygwin.base.957472714" moduleId="org.eclipse.cdt.core.settings" name="Default"> |
|||
<externalSettings/> |
|||
<extensions> |
|||
<extension id="org.eclipse.cdt.core.Cygwin_PE" point="org.eclipse.cdt.core.BinaryParser"/> |
|||
<extension id="org.eclipse.cdt.core.GmakeErrorParser" point="org.eclipse.cdt.core.ErrorParser"/> |
|||
<extension id="org.eclipse.cdt.core.CWDLocator" point="org.eclipse.cdt.core.ErrorParser"/> |
|||
<extension id="org.eclipse.cdt.core.GCCErrorParser" point="org.eclipse.cdt.core.ErrorParser"/> |
|||
<extension id="org.eclipse.cdt.core.GASErrorParser" point="org.eclipse.cdt.core.ErrorParser"/> |
|||
<extension id="org.eclipse.cdt.core.GLDErrorParser" point="org.eclipse.cdt.core.ErrorParser"/> |
|||
</extensions> |
|||
</storageModule> |
|||
<storageModule moduleId="cdtBuildSystem" version="4.0.0"> |
|||
<configuration artifactName="VendingMachine" buildProperties="" description="" id="cdt.managedbuild.toolchain.gnu.cygwin.base.957472714" name="Default" parent="org.eclipse.cdt.build.core.emptycfg"> |
|||
<folderInfo id="cdt.managedbuild.toolchain.gnu.cygwin.base.957472714.174601305" name="/" resourcePath=""> |
|||
<toolChain id="cdt.managedbuild.toolchain.gnu.cygwin.base.1500568939" name="cdt.managedbuild.toolchain.gnu.cygwin.base" superClass="cdt.managedbuild.toolchain.gnu.cygwin.base"> |
|||
<targetPlatform archList="all" binaryParser="org.eclipse.cdt.core.Cygwin_PE" id="cdt.managedbuild.target.gnu.platform.cygwin.base.1397949626" name="Debug Platform" osList="win32" superClass="cdt.managedbuild.target.gnu.platform.cygwin.base"/> |
|||
<builder id="cdt.managedbuild.target.gnu.builder.cygwin.base.607433555" keepEnvironmentInBuildfile="false" managedBuildOn="false" name="Gnu Make Builder" superClass="cdt.managedbuild.target.gnu.builder.cygwin.base"/> |
|||
<tool id="cdt.managedbuild.tool.gnu.assembler.cygwin.base.1374709500" name="GCC Assembler" superClass="cdt.managedbuild.tool.gnu.assembler.cygwin.base"> |
|||
<inputType id="cdt.managedbuild.tool.gnu.assembler.input.999469264" superClass="cdt.managedbuild.tool.gnu.assembler.input"/> |
|||
</tool> |
|||
<tool id="cdt.managedbuild.tool.gnu.archiver.cygwin.base.326519449" name="GCC Archiver" superClass="cdt.managedbuild.tool.gnu.archiver.cygwin.base"/> |
|||
<tool id="cdt.managedbuild.tool.gnu.cpp.compiler.cygwin.base.268417197" name="Cygwin C++ Compiler" superClass="cdt.managedbuild.tool.gnu.cpp.compiler.cygwin.base"> |
|||
<option id="gnu.cpp.compiler.option.include.paths.2011934454" name="Include paths (-I)" superClass="gnu.cpp.compiler.option.include.paths" valueType="includePath"/> |
|||
<option id="gnu.cpp.compiler.option.preprocessor.def.1562707910" name="Defined symbols (-D)" superClass="gnu.cpp.compiler.option.preprocessor.def" valueType="definedSymbols"> |
|||
<listOptionValue builtIn="false" value="ECLIPSE_INDEXER"/> |
|||
</option> |
|||
<inputType id="cdt.managedbuild.tool.gnu.cpp.compiler.input.cygwin.151282078" superClass="cdt.managedbuild.tool.gnu.cpp.compiler.input.cygwin"/> |
|||
</tool> |
|||
<tool id="cdt.managedbuild.tool.gnu.c.compiler.cygwin.base.459099191" name="Cygwin C Compiler" superClass="cdt.managedbuild.tool.gnu.c.compiler.cygwin.base"> |
|||
<inputType id="cdt.managedbuild.tool.gnu.c.compiler.input.cygwin.1847594251" superClass="cdt.managedbuild.tool.gnu.c.compiler.input.cygwin"/> |
|||
</tool> |
|||
<tool id="cdt.managedbuild.tool.gnu.c.linker.cygwin.base.1963503414" name="Cygwin C Linker" superClass="cdt.managedbuild.tool.gnu.c.linker.cygwin.base"/> |
|||
<tool id="cdt.managedbuild.tool.gnu.cpp.linker.cygwin.base.1943674217" name="Cygwin C++ Linker" superClass="cdt.managedbuild.tool.gnu.cpp.linker.cygwin.base"> |
|||
<inputType id="cdt.managedbuild.tool.gnu.cpp.linker.input.1639737498" superClass="cdt.managedbuild.tool.gnu.cpp.linker.input"> |
|||
<additionalInput kind="additionalinputdependency" paths="$(USER_OBJS)"/> |
|||
<additionalInput kind="additionalinput" paths="$(LIBS)"/> |
|||
</inputType> |
|||
</tool> |
|||
</toolChain> |
|||
</folderInfo> |
|||
</configuration> |
|||
</storageModule> |
|||
<storageModule moduleId="org.eclipse.cdt.core.externalSettings"/> |
|||
</cconfiguration> |
|||
</storageModule> |
|||
<storageModule moduleId="cdtBuildSystem" version="4.0.0"> |
|||
<project id="VendingMachineTarget.null.63902844" name="VendingMachineTarget"/> |
|||
</storageModule> |
|||
<storageModule moduleId="scannerConfiguration"> |
|||
<autodiscovery enabled="true" problemReportingEnabled="true" selectedProfileId=""/> |
|||
<scannerConfigBuildInfo instanceId="cdt.managedbuild.toolchain.gnu.cygwin.base.957472714;cdt.managedbuild.toolchain.gnu.cygwin.base.957472714.174601305;cdt.managedbuild.tool.gnu.cpp.compiler.cygwin.base.268417197;cdt.managedbuild.tool.gnu.cpp.compiler.input.cygwin.151282078"> |
|||
<autodiscovery enabled="true" problemReportingEnabled="true" selectedProfileId="org.eclipse.cdt.managedbuilder.core.GCCWinManagedMakePerProjectProfileCPP"/> |
|||
</scannerConfigBuildInfo> |
|||
<scannerConfigBuildInfo instanceId="cdt.managedbuild.toolchain.gnu.cygwin.base.957472714;cdt.managedbuild.toolchain.gnu.cygwin.base.957472714.174601305;cdt.managedbuild.tool.gnu.c.compiler.cygwin.base.459099191;cdt.managedbuild.tool.gnu.c.compiler.input.cygwin.1847594251"> |
|||
<autodiscovery enabled="true" problemReportingEnabled="true" selectedProfileId="org.eclipse.cdt.managedbuilder.core.GCCWinManagedMakePerProjectProfileC"/> |
|||
</scannerConfigBuildInfo> |
|||
</storageModule> |
|||
<storageModule moduleId="org.eclipse.cdt.make.core.buildtargets"> |
|||
<buildTargets> |
|||
<target name="all" path="" targetID="org.eclipse.cdt.build.MakeTargetBuilder"> |
|||
<buildCommand>make</buildCommand> |
|||
<buildArguments/> |
|||
<buildTarget>all</buildTarget> |
|||
<stopOnError>true</stopOnError> |
|||
<useDefaultCommand>true</useDefaultCommand> |
|||
<runAllBuilders>true</runAllBuilders> |
|||
</target> |
|||
<target name="clean" path="" targetID="org.eclipse.cdt.build.MakeTargetBuilder"> |
|||
<buildCommand>make</buildCommand> |
|||
<buildArguments/> |
|||
<buildTarget>clean</buildTarget> |
|||
<stopOnError>true</stopOnError> |
|||
<useDefaultCommand>true</useDefaultCommand> |
|||
<runAllBuilders>true</runAllBuilders> |
|||
</target> |
|||
</buildTargets> |
|||
</storageModule> |
|||
<storageModule moduleId="refreshScope" versionNumber="2"> |
|||
<configuration configurationName="Default"> |
|||
<resource resourceType="PROJECT" workspacePath="/VendingMachine"/> |
|||
</configuration> |
|||
</storageModule> |
|||
<storageModule moduleId="org.eclipse.cdt.core.LanguageSettingsProviders"/> |
|||
<storageModule moduleId="org.eclipse.cdt.internal.ui.text.commentOwnerProjectMappings"/> |
|||
</cproject> |
@ -0,0 +1,123 @@ |
|||
<?xml version="1.0" encoding="UTF-8"?> |
|||
<projectDescription> |
|||
<name>VendingMachineTarget</name> |
|||
<comment></comment> |
|||
<projects> |
|||
</projects> |
|||
<buildSpec> |
|||
<buildCommand> |
|||
<name>org.eclipse.cdt.managedbuilder.core.genmakebuilder</name> |
|||
<triggers>clean,full,incremental,</triggers> |
|||
<arguments> |
|||
<dictionary> |
|||
<key>?name?</key> |
|||
<value></value> |
|||
</dictionary> |
|||
<dictionary> |
|||
<key>org.eclipse.cdt.make.core.append_environment</key> |
|||
<value>true</value> |
|||
</dictionary> |
|||
<dictionary> |
|||
<key>org.eclipse.cdt.make.core.autoBuildTarget</key> |
|||
<value>all</value> |
|||
</dictionary> |
|||
<dictionary> |
|||
<key>org.eclipse.cdt.make.core.buildArguments</key> |
|||
<value></value> |
|||
</dictionary> |
|||
<dictionary> |
|||
<key>org.eclipse.cdt.make.core.buildCommand</key> |
|||
<value>make</value> |
|||
</dictionary> |
|||
<dictionary> |
|||
<key>org.eclipse.cdt.make.core.cleanBuildTarget</key> |
|||
<value>clean</value> |
|||
</dictionary> |
|||
<dictionary> |
|||
<key>org.eclipse.cdt.make.core.contents</key> |
|||
<value>org.eclipse.cdt.make.core.activeConfigSettings</value> |
|||
</dictionary> |
|||
<dictionary> |
|||
<key>org.eclipse.cdt.make.core.enableAutoBuild</key> |
|||
<value>false</value> |
|||
</dictionary> |
|||
<dictionary> |
|||
<key>org.eclipse.cdt.make.core.enableCleanBuild</key> |
|||
<value>true</value> |
|||
</dictionary> |
|||
<dictionary> |
|||
<key>org.eclipse.cdt.make.core.enableFullBuild</key> |
|||
<value>true</value> |
|||
</dictionary> |
|||
<dictionary> |
|||
<key>org.eclipse.cdt.make.core.fullBuildTarget</key> |
|||
<value>all</value> |
|||
</dictionary> |
|||
<dictionary> |
|||
<key>org.eclipse.cdt.make.core.stopOnError</key> |
|||
<value>true</value> |
|||
</dictionary> |
|||
<dictionary> |
|||
<key>org.eclipse.cdt.make.core.useDefaultBuildCmd</key> |
|||
<value>true</value> |
|||
</dictionary> |
|||
</arguments> |
|||
</buildCommand> |
|||
<buildCommand> |
|||
<name>org.eclipse.cdt.managedbuilder.core.ScannerConfigBuilder</name> |
|||
<triggers>full,incremental,</triggers> |
|||
<arguments> |
|||
</arguments> |
|||
</buildCommand> |
|||
</buildSpec> |
|||
<natures> |
|||
<nature>org.eclipse.cdt.core.cnature</nature> |
|||
<nature>org.eclipse.cdt.core.ccnature</nature> |
|||
<nature>org.eclipse.cdt.managedbuilder.core.managedBuildNature</nature> |
|||
<nature>org.eclipse.cdt.managedbuilder.core.ScannerConfigNature</nature> |
|||
</natures> |
|||
<linkedResources> |
|||
<link> |
|||
<name>build</name> |
|||
<type>2</type> |
|||
<locationURI>REL_BUILD_DIR</locationURI> |
|||
</link> |
|||
<link> |
|||
<name>project</name> |
|||
<type>2</type> |
|||
<locationURI>REL_PROJECT_DIR</locationURI> |
|||
</link> |
|||
<link> |
|||
<name>redBlocks</name> |
|||
<type>2</type> |
|||
<locationURI>REL_REDBLOCKS_DIR</locationURI> |
|||
</link> |
|||
<link> |
|||
<name>src</name> |
|||
<type>2</type> |
|||
<locationURI>REL_SRC_DIR</locationURI> |
|||
</link> |
|||
</linkedResources> |
|||
<variableList> |
|||
<variable> |
|||
<name>REL_BUILD_DIR</name> |
|||
<value>$%7BPROJECT_LOC%7D/build</value> |
|||
</variable> |
|||
<variable> |
|||
<name>REL_PROJECT_DIR</name> |
|||
<value>$%7BPROJECT_LOC%7D/project</value> |
|||
</variable> |
|||
<variable> |
|||
<name>REL_REDBLOCKS_DIR</name> |
|||
<value>$%7BPARENT-2-PROJECT_LOC%7D/redBlocks</value> |
|||
</variable> |
|||
<variable> |
|||
<name>REL_SRC_DIR</name> |
|||
<value>$%7BPROJECT_LOC%7D/src</value> |
|||
</variable> |
|||
<variable> |
|||
<name>REL_UTEST_DIR</name> |
|||
<value>$%7BPROJECT_LOC%7D/utest</value> |
|||
</variable> |
|||
</variableList> |
|||
</projectDescription> |
@ -0,0 +1,7 @@ |
|||
include paths |
|||
|
|||
# Additional compiler and linker flags can be specified here.
|
|||
COMPILER_FLAGS += |
|||
LINKER_FLAGS += |
|||
|
|||
include $(REL_REDBLOCKS_DIR)/Makefile |
@ -0,0 +1,37 @@ |
|||
<?xml version="1.0" encoding="UTF-8" standalone="no"?> |
|||
<launchConfiguration type="org.eclipse.cdt.launch.applicationLaunchType"> |
|||
<intAttribute key="org.eclipse.cdt.launch.ATTR_BUILD_BEFORE_LAUNCH_ATTR" value="1"/> |
|||
<stringAttribute key="org.eclipse.cdt.launch.COREFILE_PATH" value=""/> |
|||
<stringAttribute key="org.eclipse.cdt.launch.DEBUGGER_REGISTER_GROUPS" value=""/> |
|||
<stringAttribute key="org.eclipse.cdt.launch.PROGRAM_NAME" value="build/all/binary.exe"/> |
|||
<stringAttribute key="org.eclipse.cdt.launch.PROJECT_ATTR" value="VendingMachine"/> |
|||
<booleanAttribute key="org.eclipse.cdt.launch.PROJECT_BUILD_CONFIG_AUTO_ATTR" value="true"/> |
|||
<stringAttribute key="org.eclipse.cdt.launch.PROJECT_BUILD_CONFIG_ID_ATTR" value="cdt.managedbuild.toolchain.gnu.cygwin.base.957472714"/> |
|||
<booleanAttribute key="org.eclipse.cdt.launch.use_terminal" value="true"/> |
|||
<listAttribute key="org.eclipse.debug.core.MAPPED_RESOURCE_PATHS"> |
|||
<listEntry value="/VendingMachine"/> |
|||
</listAttribute> |
|||
<listAttribute key="org.eclipse.debug.core.MAPPED_RESOURCE_TYPES"> |
|||
<listEntry value="4"/> |
|||
</listAttribute> |
|||
<stringAttribute key="org.eclipse.debug.core.source_locator_memento" value="<?xml version="1.0" encoding="UTF-8" standalone="no"?> <sourceLookupDirector> <sourceContainers duplicates="false"> <container memento="&lt;?xml version=&quot;1.0&quot; encoding=&quot;UTF-8&quot; standalone=&quot;no&quot;?&gt;&#13;&#10;&lt;mapping name=&quot;New Mapping&quot;&gt;&#13;&#10;&lt;mapEntry memento=&quot;&amp;lt;?xml version=&amp;quot;1.0&amp;quot; encoding=&amp;quot;UTF-8&amp;quot; standalone=&amp;quot;no&amp;quot;?&amp;gt;&amp;#13;&amp;#10;&amp;lt;mapEntry backendPath=&amp;quot;\cygdrive\e&amp;quot; localPath=&amp;quot;E:\&amp;quot;/&amp;gt;&amp;#13;&amp;#10;&quot;/&gt;&#13;&#10;&lt;/mapping&gt;&#13;&#10;" typeId="org.eclipse.cdt.debug.core.containerType.mapping"/> <container memento="&lt;?xml version=&quot;1.0&quot; encoding=&quot;UTF-8&quot; standalone=&quot;no&quot;?&gt;&#13;&#10;&lt;default/&gt;&#13;&#10;" typeId="org.eclipse.debug.core.containerType.default"/> </sourceContainers> </sourceLookupDirector> "/> |
|||
<listAttribute key="org.eclipse.debug.ui.favoriteGroups"> |
|||
<listEntry value="org.eclipse.debug.ui.launchGroup.debug"/> |
|||
<listEntry value="org.eclipse.debug.ui.launchGroup.run"/> |
|||
</listAttribute> |
|||
<stringAttribute key="org.eclipse.dsf.launch.MEMORY_BLOCKS" value="<?xml version="1.0" encoding="UTF-8" standalone="no"?> <memoryBlockExpressionList context="reserved-for-future-use"/> "/> |
|||
<booleanAttribute key="org.eclipse.linuxtools.valgrind.launch.FULLPATH_AFTER" value="true"/> |
|||
<booleanAttribute key="org.eclipse.linuxtools.valgrind.launch.GENERAL_BELOWMAIN" value="false"/> |
|||
<booleanAttribute key="org.eclipse.linuxtools.valgrind.launch.GENERAL_DEMANGLE" value="true"/> |
|||
<booleanAttribute key="org.eclipse.linuxtools.valgrind.launch.GENERAL_DSYMUTIL" value="true"/> |
|||
<booleanAttribute key="org.eclipse.linuxtools.valgrind.launch.GENERAL_ERRLIMIT" value="true"/> |
|||
<booleanAttribute key="org.eclipse.linuxtools.valgrind.launch.GENERAL_FREERES" value="true"/> |
|||
<intAttribute key="org.eclipse.linuxtools.valgrind.launch.GENERAL_MAINSTACK" value="0"/> |
|||
<booleanAttribute key="org.eclipse.linuxtools.valgrind.launch.GENERAL_MAINSTACK_BOOL" value="false"/> |
|||
<intAttribute key="org.eclipse.linuxtools.valgrind.launch.GENERAL_MAXFRAME" value="2000000"/> |
|||
<intAttribute key="org.eclipse.linuxtools.valgrind.launch.GENERAL_NUMCALLERS" value="12"/> |
|||
<listAttribute key="org.eclipse.linuxtools.valgrind.launch.GENERAL_SUPPFILES"/> |
|||
<booleanAttribute key="org.eclipse.linuxtools.valgrind.launch.GENERAL_TRACECHILD" value="false"/> |
|||
<stringAttribute key="org.eclipse.linuxtools.valgrind.launch.TOOL" value="org.eclipse.linuxtools.valgrind.launch.cachegrind"/> |
|||
<stringAttribute key="process_factory_id" value="org.eclipse.cdt.dsf.gdb.GdbProcessFactory"/> |
|||
</launchConfiguration> |
@ -0,0 +1,18 @@ |
|||
# Relative path to redBlocks library |
|||
REL_REDBLOCKS_DIR = ../../redBlocks |
|||
|
|||
# Relative path to build directory |
|||
# All generated and compiled files are put into this directory. |
|||
REL_BUILD_DIR = build |
|||
|
|||
# Relative path to unit test directory. |
|||
# Unit tests are located within this directory. |
|||
REL_UTEST_DIR = utest |
|||
|
|||
# Relative path to project directory. |
|||
# Project specific sources are located within this directory. |
|||
REL_PROJECT_DIR = project |
|||
|
|||
# Relative path to source directory. |
|||
# Shared sources are located within this directory. |
|||
REL_SRC_DIR = src |
@ -0,0 +1,125 @@ |
|||
#ifndef LOW_LEVEL_PLATFORM_H_ |
|||
#define LOW_LEVEL_PLATFORM_H_ |
|||
|
|||
#include <Core/Base/NoInstanceBase.h> |
|||
#include <SimulationEnvironment.h> |
|||
#include "TKeypadDriverStub.h" |
|||
#include <OS/MainLoop/DefaultSimulationPowerSaveCallback.h> |
|||
|
|||
/**
|
|||
* This class provides a low layer hardware abstraction, making the |
|||
* layers above (high level drivers and application) independent of the |
|||
* platform they are running on. |
|||
* It defines the low level drivers for the simulation environment. |
|||
*/ |
|||
template< unsigned int T = 0 > |
|||
class TLowLevelPlatform : public redBlocks::Core::NoInstanceBase |
|||
{ |
|||
public: |
|||
|
|||
typedef redBlocks::HAL::Drivers::TDigitalInputDriverStub<0> PowerSupervision; |
|||
typedef redBlocks::HAL::Drivers::TDigitalInputDriverStub<1> LightBarrier; |
|||
typedef redBlocks::HAL::Drivers::TDigitalInputDriverStub<2> FrontDoorProtection; |
|||
typedef redBlocks::HAL::Drivers::TDigitalInputDriverStub<3> ReturnMoneyButton; |
|||
typedef redBlocks::HAL::Drivers::TDigitalInputDriverStub<4> FilledUpButton; |
|||
typedef redBlocks::HAL::Drivers::TDigitalInputDriverStub<5> Product1Button; |
|||
typedef redBlocks::HAL::Drivers::TDigitalInputDriverStub<6> Product2Button; |
|||
typedef redBlocks::HAL::Drivers::TDigitalInputDriverStub<7> Product3Button; |
|||
typedef redBlocks::HAL::Drivers::TDigitalInputDriverStub<8> Product4Button; |
|||
typedef redBlocks::HAL::Drivers::TDigitalInputDriverStub<9> StartButton; |
|||
|
|||
typedef redBlocks::HAL::Drivers::TDigitalOutputDriverStub<0> CashBoxReturnActor; |
|||
typedef redBlocks::HAL::Drivers::TDigitalOutputDriverStub<1> OpenCashBoxActor; |
|||
typedef redBlocks::HAL::Drivers::TDigitalOutputDriverStub<2> CoolingSystemActor; |
|||
typedef redBlocks::HAL::Drivers::TDigitalOutputDriverStub<3> PowerDisabledAlarmOutput; |
|||
typedef redBlocks::HAL::Drivers::TDigitalOutputDriverStub<4> KeyPadLamp; |
|||
typedef redBlocks::HAL::Drivers::TDigitalOutputDriverStub<5> KeySound; |
|||
typedef redBlocks::HAL::Drivers::TDigitalOutputDriverStub<6> ChangeBayLamp; |
|||
typedef redBlocks::HAL::Drivers::TDigitalOutputDriverStub<7> DispenseBayLamp; |
|||
typedef redBlocks::HAL::Drivers::TDigitalOutputDriverStub<8> Product1ReleaseGear; |
|||
typedef redBlocks::HAL::Drivers::TDigitalOutputDriverStub<9> Product2ReleaseGear; |
|||
typedef redBlocks::HAL::Drivers::TDigitalOutputDriverStub<10> Product3ReleaseGear; |
|||
typedef redBlocks::HAL::Drivers::TDigitalOutputDriverStub<11> Product4ReleaseGear; |
|||
typedef redBlocks::HAL::Drivers::TDigitalOutputDriverStub<12> Product1Lamp; |
|||
typedef redBlocks::HAL::Drivers::TDigitalOutputDriverStub<13> Product2Lamp; |
|||
typedef redBlocks::HAL::Drivers::TDigitalOutputDriverStub<14> Product3Lamp; |
|||
typedef redBlocks::HAL::Drivers::TDigitalOutputDriverStub<15> Product4Lamp; |
|||
typedef redBlocks::HAL::Drivers::TDigitalOutputDriverStub<16> DisplayBacklight; |
|||
|
|||
typedef redBlocks::HAL::Drivers::TAnalogInputDriverStub<0> TemperatureSensor; |
|||
|
|||
typedef redBlocks::HAL::Drivers::TComInterfaceDriverStub<0> LogComInterface; |
|||
typedef redBlocks::HAL::Drivers::TComInterfaceDriverStub<1> GsmModemComInterface; |
|||
typedef redBlocks::HAL::Drivers::TComInterfaceDriverStub<2> CoinDetectorComInterface; |
|||
typedef redBlocks::HAL::Drivers::TComInterfaceDriverStub<3> ConfigurationComInterface; |
|||
|
|||
typedef redBlocks::HAL::Drivers::TDisplayDriverStub<0> Display; |
|||
|
|||
typedef TKeypadDriverStub<10> Keypad; |
|||
|
|||
typedef redBlocks::Simulators::SimulationStubs::SystemTick SystemTickDriver; |
|||
typedef redBlocks::Simulators::SimulationStubs::IsrLock IsrLock; |
|||
typedef redBlocks::OS::MainLoopScheduler::DefaultSimulationPowerSaveCallback PowerSaveCallback; |
|||
|
|||
/**
|
|||
* Entering the sleep mode is delegated to the simulation client |
|||
*/ |
|||
static void enterSleepMode() |
|||
{ |
|||
redBlocks::Simulators::SimulationStubs::SleepMode::enter(); |
|||
} |
|||
|
|||
static void initLowLevelDrivers() |
|||
{ |
|||
typedef redBlocks::Simulators::SimulationStubs SimulationStubs; |
|||
|
|||
// configure system ticks: per simulation tick we generate 10 system ticks
|
|||
SimulationStubs::SystemTick::configure( 10, 1 ); |
|||
|
|||
SimulationStubs::DigitalInput::add<PowerSupervision>(); |
|||
SimulationStubs::DigitalInput::add<LightBarrier>( SimulationStubs::DigitalInput::TRIGGER_EDGE_BOTH ); |
|||
SimulationStubs::DigitalInput::add<FrontDoorProtection>( SimulationStubs::DigitalInput::TRIGGER_EDGE_BOTH ); |
|||
SimulationStubs::DigitalInput::add<ReturnMoneyButton>( SimulationStubs::DigitalInput::TRIGGER_EDGE_RISING ); |
|||
SimulationStubs::DigitalInput::add<FilledUpButton>( SimulationStubs::DigitalInput::TRIGGER_EDGE_RISING ); |
|||
SimulationStubs::DigitalInput::add<Product1Button>( SimulationStubs::DigitalInput::TRIGGER_EDGE_RISING ); |
|||
SimulationStubs::DigitalInput::add<Product2Button>( SimulationStubs::DigitalInput::TRIGGER_EDGE_RISING ); |
|||
SimulationStubs::DigitalInput::add<Product3Button>( SimulationStubs::DigitalInput::TRIGGER_EDGE_RISING ); |
|||
SimulationStubs::DigitalInput::add<Product4Button>( SimulationStubs::DigitalInput::TRIGGER_EDGE_RISING ); |
|||
SimulationStubs::DigitalInput::add<StartButton>( SimulationStubs::DigitalInput::TRIGGER_EDGE_RISING ); |
|||
|
|||
SimulationStubs::DigitalOutput::add<CashBoxReturnActor>( false ); |
|||
SimulationStubs::DigitalOutput::add<OpenCashBoxActor>( false ); |
|||
SimulationStubs::DigitalOutput::add<CoolingSystemActor>( false ); |
|||
SimulationStubs::DigitalOutput::add<PowerDisabledAlarmOutput>( false ); |
|||
SimulationStubs::DigitalOutput::add<KeyPadLamp>( false ); |
|||
SimulationStubs::DigitalOutput::add<KeySound>( false ); |
|||
SimulationStubs::DigitalOutput::add<ChangeBayLamp>( false ); |
|||
SimulationStubs::DigitalOutput::add<DispenseBayLamp>( false ); |
|||
SimulationStubs::DigitalOutput::add<Product1ReleaseGear>( false ); |
|||
SimulationStubs::DigitalOutput::add<Product1ReleaseGear>( false ); |
|||
SimulationStubs::DigitalOutput::add<Product2ReleaseGear>( false ); |
|||
SimulationStubs::DigitalOutput::add<Product3ReleaseGear>( false ); |
|||
SimulationStubs::DigitalOutput::add<Product4ReleaseGear>( false ); |
|||
SimulationStubs::DigitalOutput::add<Product1Lamp>( false ); |
|||
SimulationStubs::DigitalOutput::add<Product2Lamp>( false ); |
|||
SimulationStubs::DigitalOutput::add<Product3Lamp>( false ); |
|||
SimulationStubs::DigitalOutput::add<Product4Lamp>( false ); |
|||
SimulationStubs::DigitalOutput::add<DisplayBacklight>( true ); |
|||
|
|||
SimulationStubs::AnalogInput::add<TemperatureSensor> ( 255 ); |
|||
|
|||
SimulationStubs::ComInterface::add<LogComInterface> ( 1, 1 ); |
|||
SimulationStubs::ComInterface::add<GsmModemComInterface> ( 1, 1 ); |
|||
SimulationStubs::ComInterface::add<CoinDetectorComInterface> ( 1, 1 ); |
|||
|
|||
SimulationStubs::ComInterface::add<ConfigurationComInterface> ( 1, 1 ); |
|||
|
|||
SimulationStubs::Display::add<Display>( 128, 64, 1 ); |
|||
|
|||
Keypad::add(); |
|||
} |
|||
}; |
|||
|
|||
typedef TLowLevelPlatform<> LowLevelPlatform; |
|||
|
|||
#endif |
@ -0,0 +1,79 @@ |
|||
#ifndef T_KEYPAD_DRIVER_STUB_H_ |
|||
#define T_KEYPAD_DRIVER_STUB_H_ |
|||
|
|||
#include <HAL/TDriverIsrCallback.h> |
|||
#include <Simulators/IDriverStubCallback.h> |
|||
#include <Simulators/SimulationClients/ComChannelSimulationClient.h> |
|||
|
|||
|
|||
/**
|
|||
* Driver stub for a key pad. It works on a communication channel and invokes the callback |
|||
* @ref Callback::CBK_ON_KEY_PRESSED when a byte is received. |
|||
* |
|||
* @tparam T_COM_CHANNEL_INDEX specifies the number of the communication channel, this driver |
|||
* stub uses to exchange data with the simulator |
|||
*/ |
|||
template<unsigned int T_COM_CHANNEL_INDEX> |
|||
class TKeypadDriverStub: public redBlocks::Core::TGlobalPtrBase<TKeypadDriverStub<T_COM_CHANNEL_INDEX> > |
|||
{ |
|||
public: |
|||
|
|||
enum Callback |
|||
{ |
|||
CBK_ON_KEY_PRESSED |
|||
}; |
|||
|
|||
/**
|
|||
* This method initializes the driver stub (by adding the underlying logical communication channel). |
|||
* @attention Use it only during the initialization phase, as it dynamically allocates memory. |
|||
*/ |
|||
static void add() |
|||
{ |
|||
TKeypadDriverStub* self = new TKeypadDriverStub(); |
|||
redBlocks::Simulators::ComChannelSimulationClient::add( T_COM_CHANNEL_INDEX, 20, 20, &self->mInternal ); |
|||
redBlocks::Simulators::ComChannelSimulationClient::enableRecvDataCallback( T_COM_CHANNEL_INDEX ); |
|||
} |
|||
|
|||
/**
|
|||
* Should be called from the interrupt callback in order to retrieve the key that was pressed. |
|||
*/ |
|||
static u8 getKey() |
|||
{ |
|||
return TKeypadDriverStub<T_COM_CHANNEL_INDEX>::getInstanceRef().mInternal.mKey; |
|||
} |
|||
|
|||
private: |
|||
|
|||
/**
|
|||
* Internal class that implements the interface ComChannelSimulationClient::IRecvCallback |
|||
* in order to get notified, when a message is received via the communication channel. |
|||
*/ |
|||
class Internal: public redBlocks::Simulators::IDriverStubCallback |
|||
{ |
|||
public: |
|||
virtual void onDriverStubCallback() |
|||
{ |
|||
redBlocks::Simulators::ComChannelSimulationClient::RecvMsg* msg = redBlocks::Simulators::ComChannelSimulationClient::getNextMessage( T_COM_CHANNEL_INDEX ); |
|||
if( NULL != msg ) |
|||
{ |
|||
// only use the first byte of the message, the rest is ignored
|
|||
msg->read( &mKey, sizeof( mKey ) ); |
|||
// invoke the callback
|
|||
RB_INVOKE_ISR_CBK( CBK_ON_KEY_PRESSED ); |
|||
} |
|||
} |
|||
|
|||
/** the key tha was pressed */ |
|||
u8 mKey; |
|||
}; |
|||
|
|||
/** private single instance of class Internal */ |
|||
Internal mInternal; |
|||
|
|||
/**
|
|||
* Hide the constructor, as this class is meant to be instantiated only via the public method add |
|||
*/ |
|||
TKeypadDriverStub() {} |
|||
}; |
|||
|
|||
#endif // T_KEYPAD_DRIVER_STUB_H_
|
@ -0,0 +1,57 @@ |
|||
#include <Platform.h> |
|||
#include <PlatformCallbacks.h> |
|||
#include <Application/Application.h> |
|||
#include <Core/Log/Log.h> |
|||
#include <Memory/HeapManager/HeapManager.h> |
|||
|
|||
#include <Simulators/ClientPosixTcpSimulatorConnection.h> |
|||
#include <Simulators/TPosixSimulationClientEnvironmentThread.h> |
|||
#include <OS/Posix/Posix.h> |
|||
|
|||
#include <stdlib.h> |
|||
|
|||
/**
|
|||
* Main routine of our simulator application. It sets up the single components, |
|||
* associates them with each other and starts the application. |
|||
* |
|||
* Arguments: |
|||
* binary.exe [port] |
|||
*/ |
|||
int main( int argc, char* argv[] ) |
|||
{ |
|||
const u16 port = ( argc >= 2 ) ? atoi( argv[1] ) : 10000; |
|||
|
|||
typedef redBlocks::Memory::HeapManager::THeapManagerStaticAlloc<100000> HeapManager; |
|||
HeapManager::init(); |
|||
|
|||
// Connect to the simulator via TCP connection.
|
|||
redBlocks::Simulators::ClientPosixTcpSimulatorConnection simulatorConnection; |
|||
simulatorConnection.connect( "127.0.0.1", port ); |
|||
|
|||
// Setup the simulation client environment.
|
|||
// We choose the thread based version, as we are working on top of an operating system.
|
|||
redBlocks::Simulators::TPosixSimulationClientEnvironmentThread<> simClientEnv; |
|||
|
|||
// Initialize the simulation client.
|
|||
// The system tick needs to be enabled before entering this method, otherwise this method will never return.
|
|||
redBlocks::Simulators::SimulationClient simulationClient( simulatorConnection, simClientEnv ); |
|||
|
|||
// Driver initialization.
|
|||
Platform::initLowLevelDrivers(); |
|||
Platform::initHighLevelDrivers(); |
|||
|
|||
// Initialization of all simulation stubs finished.
|
|||
simulationClient.initDone(); |
|||
|
|||
// Initialize application.
|
|||
Application app; |
|||
|
|||
// Prevent dynamic memory allocation after this point.
|
|||
HeapManager::disableAllocation(); |
|||
|
|||
RB_LOG_DEBUG( "Application initialized, starting event processing" ); |
|||
RB_LOG_DEBUG( "Heap memory used: " << HeapManager::getUsed() ); |
|||
|
|||
app.run(); |
|||
} |
|||
|
@ -0,0 +1,3 @@ |
|||
// this file includes all the target dependent source files from the redBlocks library
|
|||
#include <libredBlocks_posix.cpp> |
|||
#include <libredBlocks_sim_posix.cpp> |
@ -0,0 +1,9 @@ |
|||
<?xml version="1.0" encoding="utf-8"?> |
|||
|
|||
<component_viewer schemaVersion="0.1" xmlns:xs="http://www.w3.org/2001/XMLSchema-instance" xs:noNamespaceSchemaLocation="Component_Viewer.xsd"> |
|||
|
|||
<component name="EventRecorderStub" version="1.0.0"/> <!--name and version of the component--> |
|||
<events> |
|||
</events> |
|||
|
|||
</component_viewer> |
@ -0,0 +1,253 @@ |
|||
;/**************************************************************************//** |
|||
; * @file startup_ARMCM0.s |
|||
; * @brief CMSIS Core Device Startup File for |
|||
; * ARMCM0 Device Series |
|||
; * @version V1.08 |
|||
; * @date 23. November 2012 |
|||
; * |
|||
; * @note |
|||
; * |
|||
; ******************************************************************************/ |
|||
;/* Copyright (c) 2011 - 2012 ARM LIMITED |
|||
; |
|||
; All rights reserved. |
|||
; Redistribution and use in source and binary forms, with or without |
|||
; modification, are permitted provided that the following conditions are met: |
|||
; - Redistributions of source code must retain the above copyright |
|||
; notice, this list of conditions and the following disclaimer. |
|||
; - Redistributions in binary form must reproduce the above copyright |
|||
; notice, this list of conditions and the following disclaimer in the |
|||
; documentation and/or other materials provided with the distribution. |
|||
; - Neither the name of ARM nor the names of its contributors may be used |
|||
; to endorse or promote products derived from this software without |
|||
; specific prior written permission. |
|||
; * |
|||
; THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" |
|||
; AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE |
|||
; IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE |
|||
; ARE DISCLAIMED. IN NO EVENT SHALL COPYRIGHT HOLDERS AND CONTRIBUTORS BE |
|||
; LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR |
|||
; CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF |
|||
; SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS |
|||
; INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN |
|||
; CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) |
|||
; ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE |
|||
; POSSIBILITY OF SUCH DAMAGE. |
|||
; ---------------------------------------------------------------------------*/ |
|||
;/* |
|||
;//-------- <<< Use Configuration Wizard in Context Menu >>> ------------------ |
|||
;*/ |
|||
|
|||
|
|||
; <h> Stack Configuration |
|||
; <o> Stack Size (in Bytes) <0x0-0xFFFFFFFF:8> |
|||
; </h> |
|||
|
|||
Stack_Size EQU 0x00001000 |
|||
|
|||
AREA STACK, NOINIT, READWRITE, ALIGN=3 |
|||
Stack_Mem SPACE Stack_Size |
|||
__initial_sp |
|||
|
|||
|
|||
; <h> Heap Configuration |
|||
; <o> Heap Size (in Bytes) <0x0-0xFFFFFFFF:8> |
|||
; </h> |
|||
|
|||
Heap_Size EQU 0x0000000 |
|||
|
|||
AREA HEAP, NOINIT, READWRITE, ALIGN=3 |
|||
__heap_base |
|||
Heap_Mem SPACE Heap_Size |
|||
__heap_limit |
|||
|
|||
|
|||
PRESERVE8 |
|||
THUMB |
|||
|
|||
|
|||
; Vector Table Mapped to Address 0 at Reset |
|||
|
|||
AREA RESET, DATA, READONLY |
|||
EXPORT __Vectors |
|||
EXPORT __Vectors_End |
|||
EXPORT __Vectors_Size |
|||
|
|||
__Vectors DCD __initial_sp ; Top of Stack |
|||
DCD Reset_Handler ; Reset Handler |
|||
DCD NMI_Handler ; NMI Handler |
|||
DCD HardFault_Handler ; Hard Fault Handler |
|||
DCD 0 ; Reserved |
|||
DCD 0 ; Reserved |
|||
DCD 0 ; Reserved |
|||
DCD 0 ; Reserved |
|||
DCD 0 ; Reserved |
|||
DCD 0 ; Reserved |
|||
DCD 0 ; Reserved |
|||
DCD SVC_Handler ; SVCall Handler |
|||
DCD 0 ; Reserved |
|||
DCD 0 ; Reserved |
|||
DCD PendSV_Handler ; PendSV Handler |
|||
DCD SysTick_Handler ; SysTick Handler |
|||
|
|||
; External Interrupts |
|||
DCD WDT_IRQHandler ; 0: Watchdog Timer |
|||
DCD RTC_IRQHandler ; 1: Real Time Clock |
|||
DCD TIM0_IRQHandler ; 2: Timer0 / Timer1 |
|||
DCD TIM2_IRQHandler ; 3: Timer2 / Timer3 |
|||
DCD MCIA_IRQHandler ; 4: MCIa |
|||
DCD MCIB_IRQHandler ; 5: MCIb |
|||
DCD UART0_IRQHandler ; 6: UART0 - DUT FPGA |
|||
DCD UART1_IRQHandler ; 7: UART1 - DUT FPGA |
|||
DCD UART2_IRQHandler ; 8: UART2 - DUT FPGA |
|||
DCD UART4_IRQHandler ; 9: UART4 - not connected |
|||
DCD AACI_IRQHandler ; 10: AACI / AC97 |
|||
DCD CLCD_IRQHandler ; 11: CLCD Combined Interrupt |
|||
DCD ENET_IRQHandler ; 12: Ethernet |
|||
DCD USBDC_IRQHandler ; 13: USB Device |
|||
DCD USBHC_IRQHandler ; 14: USB Host Controller |
|||
DCD CHLCD_IRQHandler ; 15: Character LCD |
|||
DCD FLEXRAY_IRQHandler ; 16: Flexray |
|||
DCD CAN_IRQHandler ; 17: CAN |
|||
DCD LIN_IRQHandler ; 18: LIN |
|||
DCD I2C_IRQHandler ; 19: I2C ADC/DAC |
|||
DCD 0 ; 20: Reserved |
|||
DCD 0 ; 21: Reserved |
|||
DCD 0 ; 22: Reserved |
|||
DCD 0 ; 23: Reserved |
|||
DCD 0 ; 24: Reserved |
|||
DCD 0 ; 25: Reserved |
|||
DCD 0 ; 26: Reserved |
|||
DCD 0 ; 27: Reserved |
|||
DCD CPU_CLCD_IRQHandler ; 28: Reserved - CPU FPGA CLCD |
|||
DCD 0 ; 29: Reserved - CPU FPGA |
|||
DCD UART3_IRQHandler ; 30: UART3 - CPU FPGA |
|||
DCD SPI_IRQHandler ; 31: SPI Touchscreen - CPU FPGA |
|||
__Vectors_End |
|||
|
|||
__Vectors_Size EQU __Vectors_End - __Vectors |
|||
|
|||
AREA |.text|, CODE, READONLY |
|||
|
|||
|
|||
; Reset Handler |
|||
|
|||
Reset_Handler PROC |
|||
EXPORT Reset_Handler [WEAK] |
|||
IMPORT SystemInit |
|||
IMPORT __main |
|||
LDR R0, =SystemInit |
|||
BLX R0 |
|||
LDR R0, =__main |
|||
BX R0 |
|||
ENDP |
|||
|
|||
|
|||
; Dummy Exception Handlers (infinite loops which can be modified) |
|||
|
|||
NMI_Handler PROC |
|||
EXPORT NMI_Handler [WEAK] |
|||
B . |
|||
ENDP |
|||
HardFault_Handler\ |
|||
PROC |
|||
EXPORT HardFault_Handler [WEAK] |
|||
B . |
|||
ENDP |
|||
SVC_Handler PROC |
|||
EXPORT SVC_Handler [WEAK] |
|||
B . |
|||
ENDP |
|||
PendSV_Handler PROC |
|||
EXPORT PendSV_Handler [WEAK] |
|||
B . |
|||
ENDP |
|||
SysTick_Handler PROC |
|||
EXPORT SysTick_Handler [WEAK] |
|||
B . |
|||
ENDP |
|||
|
|||
Default_Handler PROC |
|||
|
|||
EXPORT WDT_IRQHandler [WEAK] |
|||
EXPORT RTC_IRQHandler [WEAK] |
|||
EXPORT TIM0_IRQHandler [WEAK] |
|||
EXPORT TIM2_IRQHandler [WEAK] |
|||
EXPORT MCIA_IRQHandler [WEAK] |
|||
EXPORT MCIB_IRQHandler [WEAK] |
|||
EXPORT UART0_IRQHandler [WEAK] |
|||
EXPORT UART1_IRQHandler [WEAK] |
|||
EXPORT UART2_IRQHandler [WEAK] |
|||
EXPORT UART3_IRQHandler [WEAK] |
|||
EXPORT UART4_IRQHandler [WEAK] |
|||
EXPORT AACI_IRQHandler [WEAK] |
|||
EXPORT CLCD_IRQHandler [WEAK] |
|||
EXPORT ENET_IRQHandler [WEAK] |
|||
EXPORT USBDC_IRQHandler [WEAK] |
|||
EXPORT USBHC_IRQHandler [WEAK] |
|||
EXPORT CHLCD_IRQHandler [WEAK] |
|||
EXPORT FLEXRAY_IRQHandler [WEAK] |
|||
EXPORT CAN_IRQHandler [WEAK] |
|||
EXPORT LIN_IRQHandler [WEAK] |
|||
EXPORT I2C_IRQHandler [WEAK] |
|||
EXPORT CPU_CLCD_IRQHandler [WEAK] |
|||
EXPORT SPI_IRQHandler [WEAK] |
|||
|
|||
WDT_IRQHandler |
|||
RTC_IRQHandler |
|||
TIM0_IRQHandler |
|||
TIM2_IRQHandler |
|||
MCIA_IRQHandler |
|||
MCIB_IRQHandler |
|||
UART0_IRQHandler |
|||
UART1_IRQHandler |
|||
UART2_IRQHandler |
|||
UART3_IRQHandler |
|||
UART4_IRQHandler |
|||
AACI_IRQHandler |
|||
CLCD_IRQHandler |
|||
ENET_IRQHandler |
|||
USBDC_IRQHandler |
|||
USBHC_IRQHandler |
|||
CHLCD_IRQHandler |
|||
FLEXRAY_IRQHandler |
|||
CAN_IRQHandler |
|||
LIN_IRQHandler |
|||
I2C_IRQHandler |
|||
CPU_CLCD_IRQHandler |
|||
SPI_IRQHandler |
|||
B . |
|||
|
|||
ENDP |
|||
|
|||
|
|||
ALIGN |
|||
|
|||
|
|||
; User Initial Stack & Heap |
|||
|
|||
IF :DEF:__MICROLIB |
|||
|
|||
EXPORT __initial_sp |
|||
EXPORT __heap_base |
|||
EXPORT __heap_limit |
|||
|
|||
ELSE |
|||
|
|||
IMPORT __use_two_region_memory |
|||
EXPORT __user_initial_stackheap |
|||
|
|||
__user_initial_stackheap PROC |
|||
LDR R0, = Heap_Mem |
|||
LDR R1, =(Stack_Mem + Stack_Size) |
|||
LDR R2, = (Heap_Mem + Heap_Size) |
|||
LDR R3, = Stack_Mem |
|||
BX LR |
|||
ENDP |
|||
|
|||
ALIGN |
|||
|
|||
ENDIF |
|||
|
|||
|
|||
END |
@ -0,0 +1,86 @@ |
|||
/**************************************************************************//**
|
|||
* @file system_ARMCM0.c |
|||
* @brief CMSIS Device System Source File for |
|||
* ARMCM0 Device Series |
|||
* @version V1.09 |
|||
* @date 27. August 2014 |
|||
* |
|||
* @note |
|||
* |
|||
******************************************************************************/ |
|||
/* Copyright (c) 2011 - 2014 ARM LIMITED
|
|||
|
|||
All rights reserved. |
|||
Redistribution and use in source and binary forms, with or without |
|||
modification, are permitted provided that the following conditions are met: |
|||
- Redistributions of source code must retain the above copyright |
|||
notice, this list of conditions and the following disclaimer. |
|||
- Redistributions in binary form must reproduce the above copyright |
|||
notice, this list of conditions and the following disclaimer in the |
|||
documentation and/or other materials provided with the distribution. |
|||
- Neither the name of ARM nor the names of its contributors may be used |
|||
to endorse or promote products derived from this software without |
|||
specific prior written permission. |
|||
* |
|||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" |
|||
AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE |
|||
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE |
|||
ARE DISCLAIMED. IN NO EVENT SHALL COPYRIGHT HOLDERS AND CONTRIBUTORS BE |
|||
LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR |
|||
CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF |
|||
SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS |
|||
INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN |
|||
CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) |
|||
ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE |
|||
POSSIBILITY OF SUCH DAMAGE. |
|||
---------------------------------------------------------------------------*/ |
|||
|
|||
|
|||
#include "ARMCM0.h" |
|||
|
|||
/*----------------------------------------------------------------------------
|
|||
Define clocks |
|||
*----------------------------------------------------------------------------*/ |
|||
#define __HSI ( 8000000UL) |
|||
#define __XTAL ( 5000000UL) /* Oscillator frequency */ |
|||
|
|||
#define __SYSTEM_CLOCK (5*__XTAL) |
|||
|
|||
|
|||
/*----------------------------------------------------------------------------
|
|||
System Core Clock Variable |
|||
*----------------------------------------------------------------------------*/ |
|||
uint32_t SystemCoreClock = __SYSTEM_CLOCK;/* System Core Clock Frequency */ |
|||
|
|||
|
|||
/**
|
|||
* Update SystemCoreClock variable |
|||
* |
|||
* @param none |
|||
* @return none |
|||
* |
|||
* @brief Updates the SystemCoreClock with current core Clock |
|||
* retrieved from cpu registers. |
|||
*/ |
|||
void SystemCoreClockUpdate (void) |
|||
{ |
|||
|
|||
SystemCoreClock = __SYSTEM_CLOCK; |
|||
|
|||
} |
|||
|
|||
/**
|
|||
* Initialize the system |
|||
* |
|||
* @param none |
|||
* @return none |
|||
* |
|||
* @brief Setup the microcontroller system. |
|||
* Initialize the System. |
|||
*/ |
|||
void SystemInit (void) |
|||
{ |
|||
|
|||
SystemCoreClock = __SYSTEM_CLOCK; |
|||
|
|||
} |
@ -0,0 +1,30 @@ |
|||
|
|||
/*
|
|||
* Auto generated Run-Time-Environment Configuration File |
|||
* *** Do not modify ! *** |
|||
* |
|||
* Project: 'VendingMachine' |
|||
* Target: 'VendingMachine' |
|||
*/ |
|||
|
|||
#ifndef RTE_COMPONENTS_H |
|||
#define RTE_COMPONENTS_H |
|||
|
|||
|
|||
/*
|
|||
* Define the Device Header File: |
|||
*/ |
|||
#define CMSIS_device_header "ARMCM0.h" |
|||
|
|||
/* Keil.ARM Compiler::Compiler:I/O:STDERR:Breakpoint:1.2.0 */ |
|||
#define RTE_Compiler_IO_STDERR /* Compiler I/O: STDERR */ |
|||
#define RTE_Compiler_IO_STDERR_BKPT /* Compiler I/O: STDERR Breakpoint */ |
|||
/* Keil.ARM Compiler::Compiler:I/O:STDIN:Breakpoint:1.2.0 */ |
|||
#define RTE_Compiler_IO_STDIN /* Compiler I/O: STDIN */ |
|||
#define RTE_Compiler_IO_STDIN_BKPT /* Compiler I/O: STDIN Breakpoint */ |
|||
/* Keil.ARM Compiler::Compiler:I/O:STDOUT:Breakpoint:1.2.0 */ |
|||
#define RTE_Compiler_IO_STDOUT /* Compiler I/O: STDOUT */ |
|||
#define RTE_Compiler_IO_STDOUT_BKPT /* Compiler I/O: STDOUT Breakpoint */ |
|||
|
|||
|
|||
#endif /* RTE_COMPONENTS_H */ |
@ -0,0 +1,572 @@ |
|||
<?xml version="1.0" encoding="UTF-8" standalone="no" ?> |
|||
<Project xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="project_projx.xsd"> |
|||
|
|||
<SchemaVersion>2.1</SchemaVersion> |
|||
|
|||
<Header>### uVision Project, (C) Keil Software</Header> |
|||
|
|||
<Targets> |
|||
<Target> |
|||
<TargetName>VendingMachine</TargetName> |
|||
<ToolsetNumber>0x4</ToolsetNumber> |
|||
<ToolsetName>ARM-ADS</ToolsetName> |
|||
<pCCUsed>5060960::V5.06 update 7 (build 960)::.\ARMCC</pCCUsed> |
|||
<uAC6>0</uAC6> |
|||
<TargetOption> |
|||
<TargetCommonOption> |
|||
<Device>ARMCM0</Device> |
|||
<Vendor>ARM</Vendor> |
|||
<PackID>ARM.CMSIS.5.7.0</PackID> |
|||
<PackURL>http://www.keil.com/pack/</PackURL> |
|||
<Cpu>IROM(0x00000000,0x40000) IRAM(0x20000000,0x20000) CPUTYPE("Cortex-M0") CLOCK(12000000) ESEL ELITTLE</Cpu> |
|||
<FlashUtilSpec></FlashUtilSpec> |
|||
<StartupFile></StartupFile> |
|||
<FlashDriverDll>UL2CM3(-S0 -C0 -P0 -FD20000000 -FC1000 -FN1 -FF0NEW_DEVICE -FS00 -FL040000 -FP0($$Device:ARMCM0$Device\ARM\Flash\NEW_DEVICE.FLM))</FlashDriverDll> |
|||
<DeviceId>0</DeviceId> |
|||
<RegisterFile>$$Device:ARMCM0$Device\ARM\ARMCM0\Include\ARMCM0.h</RegisterFile> |
|||
<MemoryEnv></MemoryEnv> |
|||
<Cmp></Cmp> |
|||
<Asm></Asm> |
|||
<Linker></Linker> |
|||
<OHString></OHString> |
|||
<InfinionOptionDll></InfinionOptionDll> |
|||
<SLE66CMisc></SLE66CMisc> |
|||
<SLE66AMisc></SLE66AMisc> |
|||
<SLE66LinkerMisc></SLE66LinkerMisc> |
|||
<SFDFile>$$Device:ARMCM0$Device\ARM\SVD\ARMCM0.svd</SFDFile> |
|||
<bCustSvd>0</bCustSvd> |
|||
<UseEnv>0</UseEnv> |
|||
<BinPath></BinPath> |
|||
<IncludePath></IncludePath> |
|||
<LibPath></LibPath> |
|||
<RegisterFilePath></RegisterFilePath> |
|||
<DBRegisterFilePath></DBRegisterFilePath> |
|||
<TargetStatus> |
|||
<Error>0</Error> |
|||
<ExitCodeStop>0</ExitCodeStop> |
|||
<ButtonStop>0</ButtonStop> |
|||
<NotGenerated>0</NotGenerated> |
|||
<InvalidFlash>1</InvalidFlash> |
|||
</TargetStatus> |
|||
<OutputDirectory>.\obj\</OutputDirectory> |
|||
<OutputName>VendingMachine</OutputName> |
|||
<CreateExecutable>1</CreateExecutable> |
|||
<CreateLib>0</CreateLib> |
|||
<CreateHexFile>0</CreateHexFile> |
|||
<DebugInformation>1</DebugInformation> |
|||
<BrowseInformation>1</BrowseInformation> |
|||
<ListingPath>.\</ListingPath> |
|||
<HexFormatSelection>1</HexFormatSelection> |
|||
<Merge32K>0</Merge32K> |
|||
<CreateBatchFile>0</CreateBatchFile> |
|||
<BeforeCompile> |
|||
<RunUserProg1>0</RunUserProg1> |
|||
<RunUserProg2>0</RunUserProg2> |
|||
<UserProg1Name></UserProg1Name> |
|||
<UserProg2Name></UserProg2Name> |
|||
<UserProg1Dos16Mode>0</UserProg1Dos16Mode> |
|||
<UserProg2Dos16Mode>0</UserProg2Dos16Mode> |
|||
<nStopU1X>0</nStopU1X> |
|||
<nStopU2X>0</nStopU2X> |
|||
</BeforeCompile> |
|||
<BeforeMake> |
|||
<RunUserProg1>0</RunUserProg1> |
|||
<RunUserProg2>0</RunUserProg2> |
|||
<UserProg1Name></UserProg1Name> |
|||
<UserProg2Name></UserProg2Name> |
|||
<UserProg1Dos16Mode>0</UserProg1Dos16Mode> |
|||
<UserProg2Dos16Mode>0</UserProg2Dos16Mode> |
|||
<nStopB1X>0</nStopB1X> |
|||
<nStopB2X>0</nStopB2X> |
|||
</BeforeMake> |
|||
<AfterMake> |
|||
<RunUserProg1>0</RunUserProg1> |
|||
<RunUserProg2>0</RunUserProg2> |
|||
<UserProg1Name></UserProg1Name> |
|||
<UserProg2Name></UserProg2Name> |
|||
<UserProg1Dos16Mode>0</UserProg1Dos16Mode> |
|||
<UserProg2Dos16Mode>0</UserProg2Dos16Mode> |
|||
<nStopA1X>0</nStopA1X> |
|||
<nStopA2X>0</nStopA2X> |
|||
</AfterMake> |
|||
<SelectedForBatchBuild>0</SelectedForBatchBuild> |
|||
<SVCSIdString></SVCSIdString> |
|||
</TargetCommonOption> |
|||
<CommonProperty> |
|||
<UseCPPCompiler>0</UseCPPCompiler> |
|||
<RVCTCodeConst>0</RVCTCodeConst> |
|||
<RVCTZI>0</RVCTZI> |
|||
<RVCTOtherData>0</RVCTOtherData> |
|||
<ModuleSelection>0</ModuleSelection> |
|||
<IncludeInBuild>1</IncludeInBuild> |
|||
<AlwaysBuild>0</AlwaysBuild> |
|||
<GenerateAssemblyFile>0</GenerateAssemblyFile> |
|||
<AssembleAssemblyFile>0</AssembleAssemblyFile> |
|||
<PublicsOnly>0</PublicsOnly> |
|||
<StopOnExitCode>3</StopOnExitCode> |
|||
<CustomArgument></CustomArgument> |
|||
<IncludeLibraryModules></IncludeLibraryModules> |
|||
<ComprImg>1</ComprImg> |
|||
</CommonProperty> |
|||
<DllOption> |
|||
<SimDllName>SARMCM3.DLL</SimDllName> |
|||
<SimDllArguments> </SimDllArguments> |
|||
<SimDlgDll>DARMCM1.DLL</SimDlgDll> |
|||
<SimDlgDllArguments>-pCM0</SimDlgDllArguments> |
|||
<TargetDllName>SARMCM3.DLL</TargetDllName> |
|||
<TargetDllArguments> </TargetDllArguments> |
|||
<TargetDlgDll>TARMCM1.DLL</TargetDlgDll> |
|||
<TargetDlgDllArguments>-pCM0</TargetDlgDllArguments> |
|||
</DllOption> |
|||
<DebugOption> |
|||
<OPTHX> |
|||
<HexSelection>1</HexSelection> |
|||
<HexRangeLowAddress>0</HexRangeLowAddress> |
|||
<HexRangeHighAddress>0</HexRangeHighAddress> |
|||
<HexOffset>0</HexOffset> |
|||
<Oh166RecLen>16</Oh166RecLen> |
|||
</OPTHX> |
|||
</DebugOption> |
|||
<Utilities> |
|||
<Flash1> |
|||
<UseTargetDll>1</UseTargetDll> |
|||
<UseExternalTool>0</UseExternalTool> |
|||
<RunIndependent>0</RunIndependent> |
|||
<UpdateFlashBeforeDebugging>1</UpdateFlashBeforeDebugging> |
|||
<Capability>1</Capability> |
|||
<DriverSelection>4096</DriverSelection> |
|||
</Flash1> |
|||
<bUseTDR>1</bUseTDR> |
|||
<Flash2>BIN\UL2CM3.DLL</Flash2> |
|||
<Flash3></Flash3> |
|||
<Flash4></Flash4> |
|||
<pFcarmOut></pFcarmOut> |
|||
<pFcarmGrp></pFcarmGrp> |
|||
<pFcArmRoot></pFcArmRoot> |
|||
<FcArmLst>0</FcArmLst> |
|||
</Utilities> |
|||
<TargetArmAds> |
|||
<ArmAdsMisc> |
|||
<GenerateListings>0</GenerateListings> |
|||
<asHll>1</asHll> |
|||
<asAsm>1</asAsm> |
|||
<asMacX>1</asMacX> |
|||
<asSyms>1</asSyms> |
|||
<asFals>1</asFals> |
|||
<asDbgD>1</asDbgD> |
|||
<asForm>1</asForm> |
|||
<ldLst>0</ldLst> |
|||
<ldmm>1</ldmm> |
|||
<ldXref>1</ldXref> |
|||
<BigEnd>0</BigEnd> |
|||
<AdsALst>1</AdsALst> |
|||
<AdsACrf>1</AdsACrf> |
|||
<AdsANop>0</AdsANop> |
|||
<AdsANot>0</AdsANot> |
|||
<AdsLLst>1</AdsLLst> |
|||
<AdsLmap>1</AdsLmap> |
|||
<AdsLcgr>1</AdsLcgr> |
|||
<AdsLsym>1</AdsLsym> |
|||
<AdsLszi>1</AdsLszi> |
|||
<AdsLtoi>1</AdsLtoi> |
|||
<AdsLsun>1</AdsLsun> |
|||
<AdsLven>1</AdsLven> |
|||
<AdsLsxf>1</AdsLsxf> |
|||
<RvctClst>0</RvctClst> |
|||
<GenPPlst>0</GenPPlst> |
|||
<AdsCpuType>"Cortex-M0"</AdsCpuType> |
|||
<RvctDeviceName></RvctDeviceName> |
|||
<mOS>0</mOS> |
|||
<uocRom>0</uocRom> |
|||
<uocRam>0</uocRam> |
|||
<hadIROM>1</hadIROM> |
|||
<hadIRAM>1</hadIRAM> |
|||
<hadXRAM>0</hadXRAM> |
|||
<uocXRam>0</uocXRam> |
|||
<RvdsVP>0</RvdsVP> |
|||
<RvdsMve>0</RvdsMve> |
|||
<RvdsCdeCp>0</RvdsCdeCp> |
|||
<hadIRAM2>0</hadIRAM2> |
|||
<hadIROM2>0</hadIROM2> |
|||
<StupSel>8</StupSel> |
|||
<useUlib>0</useUlib> |
|||
<EndSel>1</EndSel> |
|||
<uLtcg>0</uLtcg> |
|||
<nSecure>0</nSecure> |
|||
<RoSelD>3</RoSelD> |
|||
<RwSelD>3</RwSelD> |
|||
<CodeSel>0</CodeSel> |
|||
<OptFeed>0</OptFeed> |
|||
<NoZi1>0</NoZi1> |
|||
<NoZi2>0</NoZi2> |
|||
<NoZi3>0</NoZi3> |
|||
<NoZi4>0</NoZi4> |
|||
<NoZi5>0</NoZi5> |
|||
<Ro1Chk>0</Ro1Chk> |
|||
<Ro2Chk>0</Ro2Chk> |
|||
<Ro3Chk>0</Ro3Chk> |
|||
<Ir1Chk>1</Ir1Chk> |
|||
<Ir2Chk>0</Ir2Chk> |
|||
<Ra1Chk>0</Ra1Chk> |
|||
<Ra2Chk>0</Ra2Chk> |
|||
<Ra3Chk>0</Ra3Chk> |
|||
<Im1Chk>1</Im1Chk> |
|||
<Im2Chk>0</Im2Chk> |
|||
<OnChipMemories> |
|||
<Ocm1> |
|||
<Type>0</Type> |
|||
<StartAddress>0x0</StartAddress> |
|||
<Size>0x0</Size> |
|||
</Ocm1> |
|||
<Ocm2> |
|||
<Type>0</Type> |
|||
<StartAddress>0x0</StartAddress> |
|||
<Size>0x0</Size> |
|||
</Ocm2> |
|||
<Ocm3> |
|||
<Type>0</Type> |
|||
<StartAddress>0x0</StartAddress> |
|||
<Size>0x0</Size> |
|||
</Ocm3> |
|||
<Ocm4> |
|||
<Type>0</Type> |
|||
<StartAddress>0x0</StartAddress> |
|||
<Size>0x0</Size> |
|||
</Ocm4> |
|||
<Ocm5> |
|||
<Type>0</Type> |
|||
<StartAddress>0x0</StartAddress> |
|||
<Size>0x0</Size> |
|||
</Ocm5> |
|||
<Ocm6> |
|||
<Type>0</Type> |
|||
<StartAddress>0x0</StartAddress> |
|||
<Size>0x0</Size> |
|||
</Ocm6> |
|||
<IRAM> |
|||
<Type>0</Type> |
|||
<StartAddress>0x20000000</StartAddress> |
|||
<Size>0x20000</Size> |
|||
</IRAM> |
|||
<IROM> |
|||
<Type>1</Type> |
|||
<StartAddress>0x0</StartAddress> |
|||
<Size>0x40000</Size> |
|||
</IROM> |
|||
<XRAM> |
|||
<Type>0</Type> |
|||
<StartAddress>0x0</StartAddress> |
|||
<Size>0x0</Size> |
|||
</XRAM> |
|||
<OCR_RVCT1> |
|||
<Type>1</Type> |
|||
<StartAddress>0x0</StartAddress> |
|||
<Size>0x0</Size> |
|||
</OCR_RVCT1> |
|||
<OCR_RVCT2> |
|||
<Type>1</Type> |
|||
<StartAddress>0x0</StartAddress> |
|||
<Size>0x0</Size> |
|||
</OCR_RVCT2> |
|||
<OCR_RVCT3> |
|||
<Type>1</Type> |
|||
<StartAddress>0x0</StartAddress> |
|||
<Size>0x0</Size> |
|||
</OCR_RVCT3> |
|||
<OCR_RVCT4> |
|||
<Type>1</Type> |
|||
<StartAddress>0x0</StartAddress> |
|||
<Size>0x40000</Size> |
|||
</OCR_RVCT4> |
|||
<OCR_RVCT5> |
|||
<Type>1</Type> |
|||
<StartAddress>0x0</StartAddress> |
|||
<Size>0x0</Size> |
|||
</OCR_RVCT5> |
|||
<OCR_RVCT6> |
|||
<Type>0</Type> |
|||
<StartAddress>0x0</StartAddress> |
|||
<Size>0x0</Size> |
|||
</OCR_RVCT6> |
|||
<OCR_RVCT7> |
|||
<Type>0</Type> |
|||
<StartAddress>0x0</StartAddress> |
|||
<Size>0x0</Size> |
|||
</OCR_RVCT7> |
|||
<OCR_RVCT8> |
|||
<Type>0</Type> |
|||
<StartAddress>0x0</StartAddress> |
|||
<Size>0x0</Size> |
|||
</OCR_RVCT8> |
|||
<OCR_RVCT9> |
|||
<Type>0</Type> |
|||
<StartAddress>0x20000000</StartAddress> |
|||
<Size>0x20000</Size> |
|||
</OCR_RVCT9> |
|||
<OCR_RVCT10> |
|||
<Type>0</Type> |
|||
<StartAddress>0x0</StartAddress> |
|||
<Size>0x0</Size> |
|||
</OCR_RVCT10> |
|||
</OnChipMemories> |
|||
<RvctStartVector></RvctStartVector> |
|||
</ArmAdsMisc> |
|||
<Cads> |
|||
<interw>1</interw> |
|||
<Optim>4</Optim> |
|||
<oTime>0</oTime> |
|||
<SplitLS>0</SplitLS> |
|||
<OneElfS>1</OneElfS> |
|||
<Strict>0</Strict> |
|||
<EnumInt>0</EnumInt> |
|||
<PlainCh>0</PlainCh> |
|||
<Ropi>0</Ropi> |
|||
<Rwpi>0</Rwpi> |
|||
<wLevel>0</wLevel> |
|||
<uThumb>0</uThumb> |
|||
<uSurpInc>0</uSurpInc> |
|||
<uC99>0</uC99> |
|||
<uGnu>0</uGnu> |
|||
<useXO>0</useXO> |
|||
<v6Lang>1</v6Lang> |
|||
<v6LangP>1</v6LangP> |
|||
<vShortEn>1</vShortEn> |
|||
<vShortWch>1</vShortWch> |
|||
<v6Lto>0</v6Lto> |
|||
<v6WtE>0</v6WtE> |
|||
<v6Rtti>0</v6Rtti> |
|||
<VariousControls> |
|||
<MiscControls>--diag_suppress 1300 --no_rtti --no_exceptions</MiscControls> |
|||
<Define></Define> |
|||
<Undefine></Undefine> |
|||
<IncludePath>..;..\..;..\..\..;..\..\..\..\src;..\..\..\..\src\Application;..\..\..\..\..\..\redBlocks\src;..\..\..\..\..\..\redBlocks\inc</IncludePath> |
|||
</VariousControls> |
|||
</Cads> |
|||
<Aads> |
|||
<interw>1</interw> |
|||
<Ropi>0</Ropi> |
|||
<Rwpi>0</Rwpi> |
|||
<thumb>0</thumb> |
|||
<SplitLS>0</SplitLS> |
|||
<SwStkChk>0</SwStkChk> |
|||
<NoWarn>0</NoWarn> |
|||
<uSurpInc>0</uSurpInc> |
|||
<useXO>0</useXO> |
|||
<ClangAsOpt>4</ClangAsOpt> |
|||
<VariousControls> |
|||
<MiscControls></MiscControls> |
|||
<Define></Define> |
|||
<Undefine></Undefine> |
|||
<IncludePath></IncludePath> |
|||
</VariousControls> |
|||
</Aads> |
|||
<LDads> |
|||
<umfTarg>0</umfTarg> |
|||
<Ropi>0</Ropi> |
|||
<Rwpi>0</Rwpi> |
|||
<noStLib>0</noStLib> |
|||
<RepFail>1</RepFail> |
|||
<useFile>0</useFile> |
|||
<TextAddressRange>0x00000000</TextAddressRange> |
|||
<DataAddressRange>0x20000000</DataAddressRange> |
|||
<pXoBase></pXoBase> |
|||
<ScatterFile></ScatterFile> |
|||
<IncludeLibs></IncludeLibs> |
|||
<IncludeLibsPath></IncludeLibsPath> |
|||
<Misc></Misc> |
|||
<LinkerInputFile></LinkerInputFile> |
|||
<DisabledWarnings></DisabledWarnings> |
|||
</LDads> |
|||
</TargetArmAds> |
|||
</TargetOption> |
|||
<Groups> |
|||
<Group> |
|||
<GroupName>Source Files</GroupName> |
|||
<Files> |
|||
<File> |
|||
<FileName>main.cpp</FileName> |
|||
<FileType>8</FileType> |
|||
<FilePath>main.cpp</FilePath> |
|||
</File> |
|||
<File> |
|||
<FileName>AlarmManager.cpp</FileName> |
|||
<FileType>8</FileType> |
|||
<FilePath>..\..\..\..\src\Application\AlarmManager.cpp</FilePath> |
|||
</File> |
|||
<File> |
|||
<FileName>Application.cpp</FileName> |
|||
<FileType>8</FileType> |
|||
<FilePath>..\..\..\..\src\Application\Application.cpp</FilePath> |
|||
</File> |
|||
<File> |
|||
<FileName>CashBox.cpp</FileName> |
|||
<FileType>8</FileType> |
|||
<FilePath>..\..\..\..\src\Application\CashBox.cpp</FilePath> |
|||
</File> |
|||
<File> |
|||
<FileName>GlobalState.cpp</FileName> |
|||
<FileType>8</FileType> |
|||
<FilePath>..\..\..\..\src\Application\GlobalState.cpp</FilePath> |
|||
</File> |
|||
<File> |
|||
<FileName>MaintenanceMode.cpp</FileName> |
|||
<FileType>8</FileType> |
|||
<FilePath>..\..\..\..\src\Application\MaintenanceMode.cpp</FilePath> |
|||
</File> |
|||
<File> |
|||
<FileName>ProductSlot.cpp</FileName> |
|||
<FileType>8</FileType> |
|||
<FilePath>..\..\..\..\src\Application\ProductSlot.cpp</FilePath> |
|||
</File> |
|||
<File> |
|||
<FileName>VendingMode.cpp</FileName> |
|||
<FileType>8</FileType> |
|||
<FilePath>..\..\..\..\src\Application\VendingMode.cpp</FilePath> |
|||
</File> |
|||
<File> |
|||
<FileName>MaintenanceScreen.cpp</FileName> |
|||
<FileType>8</FileType> |
|||
<FilePath>..\..\..\..\src\Gui\MaintenanceScreen.cpp</FilePath> |
|||
</File> |
|||
<File> |
|||
<FileName>VendingScreen.cpp</FileName> |
|||
<FileType>8</FileType> |
|||
<FilePath>..\..\..\..\src\Gui\VendingScreen.cpp</FilePath> |
|||
</File> |
|||
<File> |
|||
<FileName>Arial20.cpp</FileName> |
|||
<FileType>8</FileType> |
|||
<FilePath>..\..\..\..\src\Gui\GuiData\Arial20.cpp</FilePath> |
|||
</File> |
|||
<File> |
|||
<FileName>Images.cpp</FileName> |
|||
<FileType>8</FileType> |
|||
<FilePath>..\..\..\..\src\Gui\GuiData\Images.cpp</FilePath> |
|||
</File> |
|||
<File> |
|||
<FileName>redBlocksEnv.cpp</FileName> |
|||
<FileType>8</FileType> |
|||
<FilePath>.\redBlocksEnv.cpp</FilePath> |
|||
</File> |
|||
<File> |
|||
<FileName>redBlocksLib.cpp</FileName> |
|||
<FileType>8</FileType> |
|||
<FilePath>..\..\..\..\src\redBlocksLib.cpp</FilePath> |
|||
</File> |
|||
</Files> |
|||
</Group> |
|||
<Group> |
|||
<GroupName>Libs</GroupName> |
|||
<Files> |
|||
<File> |
|||
<FileName>libredBlocks_uvision.lib</FileName> |
|||
<FileType>4</FileType> |
|||
<FilePath>..\..\..\..\..\..\redBlocks\libredBlocks_uvision.lib</FilePath> |
|||
<FileOption> |
|||
<CommonProperty> |
|||
<UseCPPCompiler>2</UseCPPCompiler> |
|||
<RVCTCodeConst>0</RVCTCodeConst> |
|||
<RVCTZI>0</RVCTZI> |
|||
<RVCTOtherData>0</RVCTOtherData> |
|||
<ModuleSelection>0</ModuleSelection> |
|||
<IncludeInBuild>1</IncludeInBuild> |
|||
<AlwaysBuild>2</AlwaysBuild> |
|||
<GenerateAssemblyFile>2</GenerateAssemblyFile> |
|||
<AssembleAssemblyFile>2</AssembleAssemblyFile> |
|||
<PublicsOnly>2</PublicsOnly> |
|||
<StopOnExitCode>11</StopOnExitCode> |
|||
<CustomArgument></CustomArgument> |
|||
<IncludeLibraryModules></IncludeLibraryModules> |
|||
<ComprImg>1</ComprImg> |
|||
</CommonProperty> |
|||
<FileArmAds/> |
|||
</FileOption> |
|||
</File> |
|||
</Files> |
|||
</Group> |
|||
<Group> |
|||
<GroupName>::CMSIS</GroupName> |
|||
</Group> |
|||
<Group> |
|||
<GroupName>::Compiler</GroupName> |
|||
</Group> |
|||
<Group> |
|||
<GroupName>::Device</GroupName> |
|||
</Group> |
|||
</Groups> |
|||
</Target> |
|||
</Targets> |
|||
|
|||
<RTE> |
|||
<apis/> |
|||
<components> |
|||
<component Cclass="CMSIS" Cgroup="CORE" Cvendor="ARM" Cversion="5.4.0" condition="ARMv6_7_8-M Device"> |
|||
<package name="CMSIS" schemaVersion="1.3" url="http://www.keil.com/pack/" vendor="ARM" version="5.7.0"/> |
|||
<targetInfos> |
|||
<targetInfo name="VendingMachine"/> |
|||
</targetInfos> |
|||
</component> |
|||
<component Cclass="Device" Cgroup="Startup" Cvendor="ARM" Cversion="1.2.2" condition="ARMCM0 CMSIS"> |
|||
<package name="CMSIS" schemaVersion="1.3" url="http://www.keil.com/pack/" vendor="ARM" version="5.7.0"/> |
|||
<targetInfos> |
|||
<targetInfo name="VendingMachine"/> |
|||
</targetInfos> |
|||
</component> |
|||
<component Cbundle="ARM Compiler" Cclass="Compiler" Cgroup="I/O" Csub="STDERR" Cvariant="Breakpoint" Cvendor="Keil" Cversion="1.2.0" condition="ARMCC Cortex-M"> |
|||
<package name="ARM_Compiler" schemaVersion="1.6.3" url="http://www.keil.com/pack/" vendor="Keil" version="1.6.3"/> |
|||
<targetInfos> |
|||
<targetInfo name="VendingMachine"/> |
|||
</targetInfos> |
|||
</component> |
|||
<component Cbundle="ARM Compiler" Cclass="Compiler" Cgroup="I/O" Csub="STDIN" Cvariant="Breakpoint" Cvendor="Keil" Cversion="1.2.0" condition="ARMCC Cortex-M"> |
|||
<package name="ARM_Compiler" schemaVersion="1.6.3" url="http://www.keil.com/pack/" vendor="Keil" version="1.6.3"/> |
|||
<targetInfos> |
|||
<targetInfo name="VendingMachine"/> |
|||
</targetInfos> |
|||
</component> |
|||
<component Cbundle="ARM Compiler" Cclass="Compiler" Cgroup="I/O" Csub="STDOUT" Cvariant="Breakpoint" Cvendor="Keil" Cversion="1.2.0" condition="ARMCC Cortex-M"> |
|||
<package name="ARM_Compiler" schemaVersion="1.6.3" url="http://www.keil.com/pack/" vendor="Keil" version="1.6.3"/> |
|||
<targetInfos> |
|||
<targetInfo name="VendingMachine"/> |
|||
</targetInfos> |
|||
</component> |
|||
</components> |
|||
<files> |
|||
<file attr="config" category="sourceAsm" condition="ARMCC" name="Device\ARM\ARMCM0\Source\ARM\startup_ARMCM0.s" version="1.0.0"> |
|||
<instance index="0">RTE\Device\ARMCM0\startup_ARMCM0.s</instance> |
|||
<component Cclass="Device" Cgroup="Startup" Cvendor="ARM" Cversion="1.2.2" condition="ARMCM0 CMSIS"/> |
|||
<package name="CMSIS" schemaVersion="1.3" url="http://www.keil.com/pack/" vendor="ARM" version="5.7.0"/> |
|||
<targetInfos> |
|||
<targetInfo name="VendingMachine"/> |
|||
</targetInfos> |
|||
</file> |
|||
<file attr="config" category="sourceC" name="Device\ARM\ARMCM0\Source\system_ARMCM0.c" version="1.0.0"> |
|||
<instance index="0">RTE\Device\ARMCM0\system_ARMCM0.c</instance> |
|||
<component Cclass="Device" Cgroup="Startup" Cvendor="ARM" Cversion="1.2.2" condition="ARMCM0 CMSIS"/> |
|||
<package name="CMSIS" schemaVersion="1.3" url="http://www.keil.com/pack/" vendor="ARM" version="5.7.0"/> |
|||
<targetInfos> |
|||
<targetInfo name="VendingMachine"/> |
|||
</targetInfos> |
|||
</file> |
|||
<file attr="config" category="doc" name="Readme.txt" version="0.0.0"> |
|||
<instance index="0" removed="1">RTE\Simulator\Readme.txt</instance> |
|||
<component Cclass="Simulator" Cgroup="C-API" Cvendor="redlogix" Cversion="" condition=""/> |
|||
<package name="Simulator" schemaVersion="1.2" url="http://www.keil.com/pack/" vendor="redlogix" version="2.1.0"/> |
|||
<targetInfos/> |
|||
</file> |
|||
<file attr="config" category="header" name="redBlocks\src\libredBlocks_sim.h" version="0.0.0"> |
|||
<instance index="0" removed="1">RTE\Simulator\libredBlocks_sim.h</instance> |
|||
<component Cclass="Simulator" Cgroup="C-API" Cvendor="redlogix" Cversion="" condition=""/> |
|||
<package name="Simulator" schemaVersion="1.2" url="http://www.keil.com/pack/" vendor="redlogix" version="2.1.0"/> |
|||
<targetInfos/> |
|||
</file> |
|||
<file attr="config" category="header" name="redBlocks\src\libredBlocks_sim_uvision.h" version="0.0.0"> |
|||
<instance index="0" removed="1">RTE\Simulator\libredBlocks_sim_uvision.h</instance> |
|||
<component Cclass="Simulator" Cgroup="C-API" Cvendor="redlogix" Cversion="" condition=""/> |
|||
<package name="Simulator" schemaVersion="1.2" url="http://www.keil.com/pack/" vendor="redlogix" version="2.1.0"/> |
|||
<targetInfos/> |
|||
</file> |
|||
</files> |
|||
</RTE> |
|||
|
|||
</Project> |
@ -0,0 +1,101 @@ |
|||
// TODO
|
|||
// When changing the device in the project settings, adjust the following include accordingly and
|
|||
// set the heap and stack size in the startup file to reasonable values (as this project includes
|
|||
// a redBlocks heap manager, which maintains its memory in the global data section, the heap size
|
|||
// in the startup file can be set to 0).
|
|||
#include <ARMCM0.h> |
|||
|
|||
#include <Platform.h> |
|||
#include <PlatformCallbacks.h> |
|||
#include <Application/Application.h> |
|||
#include <Core/Log/Log.h> |
|||
#include <Memory/HeapManager/HeapManager.h> |
|||
|
|||
#include <HAL/Drivers/Cortex/CortexMSystemTickDriver.h> |
|||
#include <Simulators/TargetConnection/UVisionClientTargetConnection.h> |
|||
#include <Simulators/TSystemTickSimulationClientEnvironment.h> |
|||
|
|||
typedef redBlocks::Simulators::UVisionClientTargetConnection TargetConnectionType; |
|||
|
|||
typedef redBlocks::HAL::Drivers::CortexMSystemTickDriver SystemTickDriver; |
|||
RB_CONNECT_ISR_CBK( SystemTickDriver, SystemTickDriver::CBK_ON_SYSTEM_TICK, redBlocks::Simulators::SimulationClient::tick() ); |
|||
|
|||
static const u32 SYSTEM_TICKS_PER_SEC = 100; |
|||
|
|||
static bool should_continue = false; |
|||
|
|||
extern "C" |
|||
{ |
|||
void SysTick_Handler( void ) |
|||
{ |
|||
SystemTickDriver::onIsr(); |
|||
} |
|||
|
|||
void onStartPressed( void ) |
|||
{ |
|||
should_continue=true; |
|||
} |
|||
|
|||
void getChange( u16 moneyInBox, u16 itemPrice ) |
|||
{ |
|||
u8 change = moneyInBox - itemPrice; |
|||
char changeMessage[22]; |
|||
sprintf(changeMessage, "Your change: %d", change); |
|||
RB_LOG_DEBUG( changeMessage ); |
|||
} |
|||
} |
|||
|
|||
int main( void ) |
|||
{ |
|||
// For correct timing, you need to make sure this value corresponds to the setting
|
|||
// "Xtal (MHz)" in the Keil uVision target option settings (e. g. 8.0 MHz => 8000000)
|
|||
SystemCoreClock = 8000000; |
|||
|
|||
typedef redBlocks::Memory::HeapManager::THeapManagerStaticAlloc<6000> HeapManager; |
|||
HeapManager::init(); |
|||
|
|||
// The data with the redBlocks Simulator is exchanged via a target memory area, the
|
|||
// redBlocks Simulator accesses via the uVision UVSOCK interface. The memory region
|
|||
// must be exclusively reserved for this purpose (e. g. via the Keil uVision target
|
|||
// option settings, tab Debug -> Initialization File.
|
|||
// With the following line, the memory at address 0x30000000 and a default size of
|
|||
// 1052 bytes is used (52 bytes for control information plus a send and receive
|
|||
// buffer with 500 bytes each).
|
|||
TargetConnectionType simulatorConnection( 0x30000000 ); |
|||
simulatorConnection.connect(); |
|||
|
|||
// Setup the simulation client environment.
|
|||
redBlocks::Simulators::TSystemTickSimulationClientEnvironment<SystemTickDriver> simClientEnv; |
|||
|
|||
// Enable system tick.
|
|||
SystemTickDriver::configure( SYSTEM_TICKS_PER_SEC ); |
|||
SystemTickDriver::enableCallback(); |
|||
|
|||
// Initialize the simulation client.
|
|||
// The system tick needs to be enabled before entering this method, otherwise this method will never return.
|
|||
redBlocks::Simulators::SimulationClient simulationClient( simulatorConnection, simClientEnv ); |
|||
|
|||
// Driver initialization.
|
|||
Platform::initLowLevelDrivers(); |
|||
Platform::initHighLevelDrivers(); |
|||
|
|||
// Initialization of all simulation stubs finished.
|
|||
simulationClient.initDone(); |
|||
|
|||
// Application initialization.
|
|||
Application app; |
|||
|
|||
// Prevent dynamic memory allocation after this point.
|
|||
HeapManager::disableAllocation(); |
|||
|
|||
RB_LOG_DEBUG( "Application initialized, starting event processing" ); |
|||
RB_LOG_DEBUG( "Heap memory used:" << HeapManager::getUsed() ); |
|||
|
|||
RB_LOG_DEBUG( "Waiting to start..." ); |
|||
while(!should_continue) { |
|||
__WFI(); |
|||
} |
|||
RB_LOG_DEBUG( "Starting." ); |
|||
|
|||
app.run(); |
|||
} |
@ -0,0 +1,2 @@ |
|||
// this file includes all the target dependent source files from the redBlocks library
|
|||
#include <libredBlocks_uvision.cpp> |
File diff suppressed because one or more lines are too long
After Width: | Height: | Size: 1.2 KiB |
After Width: | Height: | Size: 1.3 KiB |
@ -0,0 +1,34 @@ |
|||
#!/usr/bin/python |
|||
from redBlocks import * |
|||
|
|||
def enableCallback(sc, interface, value): |
|||
if sc.SBO("EnableCoolingSystem").getValue(): |
|||
print( "Cooling system enabled" ) |
|||
else: |
|||
print( "Cooling system disabled" ) |
|||
|
|||
scf = SimulatorConnectionFactory() |
|||
scf.registerSBO("EnableCoolingSystem", enableCallback) |
|||
scf.registerAI("Temperature Sensor") |
|||
scf.registerDO("Cooling System Actor") |
|||
sc = scf.create() |
|||
|
|||
sc.SBO("EnableCoolingSystem").setValue(True) |
|||
|
|||
while (True): |
|||
sc.lock() |
|||
|
|||
if sc.isSimulationRunning() and sc.SBO("EnableCoolingSystem").getValue(): |
|||
temperature = sc.AI("Temperature Sensor").getValue() |
|||
if sc.DO("Cooling System Actor").getValue(): |
|||
temperature -= 3 |
|||
if temperature < 0: |
|||
temperature = 0 |
|||
else: |
|||
temperature += 1 |
|||
if temperature > 255: |
|||
temperature = 255 |
|||
sc.AI("Temperature Sensor").setValue(temperature) |
|||
|
|||
sc.unlock() |
|||
sleep(0.5) |
@ -0,0 +1,27 @@ |
|||
#!/usr/bin/python |
|||
from redBlocks import * |
|||
|
|||
def coinCallback(sc,interface,value): |
|||
if value : |
|||
print( "Button " + interface.getName() + " pressed." ) |
|||
if "Euro200" == interface.getName(): |
|||
value = "4" |
|||
elif "Euro100" == interface.getName(): |
|||
value = "3" |
|||
elif "Euro50" == interface.getName(): |
|||
value = "2" |
|||
elif "Euro20" == interface.getName(): |
|||
value = "1" |
|||
elif "Euro10" == interface.getName(): |
|||
value = "0" |
|||
sc.CC("Coin Detector").sendMessage( value ) |
|||
|
|||
scf = SimulatorConnectionFactory() |
|||
scf.registerCC("Coin Detector") |
|||
scf.registerSBO("Euro200", coinCallback) |
|||
scf.registerSBO("Euro100", coinCallback) |
|||
scf.registerSBO("Euro50", coinCallback) |
|||
scf.registerSBO("Euro20", coinCallback) |
|||
scf.registerSBO("Euro10", coinCallback) |
|||
sc = scf.create() |
|||
loopForever() |
@ -0,0 +1,25 @@ |
|||
#!/usr/bin/python |
|||
from redBlocks import * |
|||
|
|||
def keyPadCallback(sc, interface,value): |
|||
if value: |
|||
key = ord(interface.getName()[6]) - 0x30 |
|||
print( "Key " + interface.getName()[6] + " pressed." ) |
|||
sc.CC("Keypad").sendMessage( bytearray([key]) ) |
|||
|
|||
scf = SimulatorConnectionFactory() |
|||
|
|||
scf.registerCC("Keypad") |
|||
scf.registerSBO("KeyPad0", keyPadCallback) |
|||
scf.registerSBO("KeyPad1", keyPadCallback) |
|||
scf.registerSBO("KeyPad2", keyPadCallback) |
|||
scf.registerSBO("KeyPad3", keyPadCallback) |
|||
scf.registerSBO("KeyPad4", keyPadCallback) |
|||
scf.registerSBO("KeyPad5", keyPadCallback) |
|||
scf.registerSBO("KeyPad6", keyPadCallback) |
|||
scf.registerSBO("KeyPad7", keyPadCallback) |
|||
scf.registerSBO("KeyPad8", keyPadCallback) |
|||
scf.registerSBO("KeyPad9", keyPadCallback) |
|||
sc = scf.create() |
|||
|
|||
loopForever() |
@ -0,0 +1,22 @@ |
|||
#!/usr/bin/python |
|||
from redBlocks import * |
|||
|
|||
def releaseProductCallback(sc, interface,value): |
|||
if value and sc.SBO("Automatic light barrier").getValue(): |
|||
sc.DI("Light Barrier").setValue(True) |
|||
sleep(0.01) |
|||
sc.DI("Light Barrier").setValue(False) |
|||
print( "Product released" ) |
|||
|
|||
scf = SimulatorConnectionFactory() |
|||
scf.registerDO("Product 1 Release Gear", releaseProductCallback) |
|||
scf.registerDO("Product 2 Release Gear", releaseProductCallback) |
|||
scf.registerDO("Product 3 Release Gear", releaseProductCallback) |
|||
scf.registerDO("Product 4 Release Gear", releaseProductCallback) |
|||
scf.registerDI("Light Barrier") |
|||
scf.registerSBO("Automatic light barrier") |
|||
sc = scf.create() |
|||
|
|||
sc.SBO("Automatic light barrier").setValue(True) |
|||
|
|||
loopForever() |
@ -0,0 +1,293 @@ |
|||
#!/usr/bin/python |
|||
from redBlocks import * |
|||
from redBlocksTest import * |
|||
|
|||
# This script was generated by the redBlocks Simulator's test script recorder. |
|||
# It serves for demonstration purposes and tests the application's behaviour when a product slot is blocked, so the bottle cannot be realeased. |
|||
# It needs to be started with all slots being unblocked and will leave the first slot being blocked. |
|||
|
|||
scf = SimulatorConnectionFactory() |
|||
|
|||
# Registration of interfaces |
|||
scf.registerDO("Product 4 Lamp") |
|||
scf.registerDO("Product 3 Lamp") |
|||
scf.registerDO("Product 2 Lamp") |
|||
scf.registerDO("Product 1 Lamp") |
|||
scf.registerDO("Dispense Bay Lamp") |
|||
scf.registerDO("Change Bay Lamp") |
|||
scf.registerDO("Open Cash Box Actor") |
|||
scf.registerDO("Cash Box Return Actor") |
|||
scf.registerDO("Product 1 Release Gear") |
|||
scf.registerDO("Product 2 Release Gear") |
|||
scf.registerDO("Product 3 Release Gear") |
|||
scf.registerDO("Product 4 Release Gear") |
|||
scf.registerCC("GSM Modem") |
|||
scf.registerDP("Display") |
|||
scf.registerSBO("Automatic light barrier") |
|||
scf.registerDI("Product 4 Button") |
|||
scf.registerSBO("Euro100") |
|||
scf.registerDI("Return Money Button") |
|||
sc = scf.create() |
|||
|
|||
# Define set of interfaces to observe |
|||
observer = Observer() |
|||
observer.add(sc.DO("Product 4 Lamp")) |
|||
observer.add(sc.DO("Product 3 Lamp")) |
|||
observer.add(sc.DO("Product 2 Lamp")) |
|||
observer.add(sc.DO("Product 1 Lamp")) |
|||
observer.add(sc.DO("Dispense Bay Lamp")) |
|||
observer.add(sc.DO("Change Bay Lamp")) |
|||
observer.add(sc.DO("Open Cash Box Actor")) |
|||
observer.add(sc.DO("Cash Box Return Actor")) |
|||
observer.add(sc.DO("Product 1 Release Gear")) |
|||
observer.add(sc.DO("Product 2 Release Gear")) |
|||
observer.add(sc.DO("Product 3 Release Gear")) |
|||
observer.add(sc.DO("Product 4 Release Gear")) |
|||
observer.add(sc.CC("GSM Modem"), 0.10) |
|||
observer.add(sc.DP("Display"), 0.10) |
|||
|
|||
# time tolerance: adjust to a suitable value depending on the latency of the test setup |
|||
TOL = 0.20 |
|||
observer.setTolerance(TOL) |
|||
|
|||
observer.start() |
|||
time = observer.getTime() |
|||
|
|||
|
|||
# Test Preconditions |
|||
observer[sc.DO("Product 4 Lamp")].checkData(False) |
|||
observer[sc.DO("Product 3 Lamp")].checkData(False) |
|||
observer[sc.DO("Product 2 Lamp")].checkData(False) |
|||
observer[sc.DO("Product 1 Lamp")].checkData(False) |
|||
observer[sc.DO("Dispense Bay Lamp")].checkData(False) |
|||
observer[sc.DO("Change Bay Lamp")].checkData(False) |
|||
observer[sc.DO("Open Cash Box Actor")].checkData(True) |
|||
observer[sc.DO("Cash Box Return Actor")].checkData(False) |
|||
observer[sc.DO("Product 1 Release Gear")].checkData(False) |
|||
observer[sc.DO("Product 2 Release Gear")].checkData(False) |
|||
observer[sc.DO("Product 3 Release Gear")].checkData(False) |
|||
observer[sc.DO("Product 4 Release Gear")].checkData(False) |
|||
observer[sc.DP("Display")].checkData(DisplayData.fromFileContents(binaryData('0.rbb'))) |
|||
|
|||
observer.sleep(1.153) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("Automatic light barrier").setValue(False) |
|||
|
|||
observer.sleep(1.530) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Product 4 Button").setValue(True) |
|||
|
|||
observer[sc.DO("Product 4 Lamp")].addNoChangeCheck(time + 0.03 - TOL) |
|||
observer[sc.DO("Product 4 Lamp")].addEventCheck(time + 0.03 + TOL, True) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.03 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.03 + TOL, DisplayData.fromFileContents(binaryData('1.rbb'))) |
|||
|
|||
observer.sleep(0.091) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Product 4 Button").setValue(False) |
|||
|
|||
observer.sleep(1.002) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("Euro100").setValue(True) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.04 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.04 + TOL, DisplayData.fromFileContents(binaryData('2.rbb'))) |
|||
|
|||
observer.sleep(0.295) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("Euro100").setValue(False) |
|||
|
|||
observer.sleep(0.696) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("Euro100").setValue(True) |
|||
|
|||
observer[sc.DO("Product 4 Release Gear")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DO("Product 4 Release Gear")].addEventCheck(time + 0.02 + TOL, True) |
|||
|
|||
observer[sc.DO("Product 4 Lamp")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DO("Product 4 Lamp")].addEventCheck(time + 0.02 + TOL, False) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.03 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.03 + TOL, DisplayData.fromFileContents(binaryData('3.rbb'))) |
|||
|
|||
observer.sleep(0.303) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("Euro100").setValue(False) |
|||
|
|||
observer[sc.DO("Product 4 Release Gear")].addNoChangeCheck(time + 0.72 - TOL) |
|||
observer[sc.DO("Product 4 Release Gear")].addEventCheck(time + 0.72 + TOL, False) |
|||
|
|||
observer[sc.DO("Product 4 Release Gear")].addNoChangeCheck(time + 1.22 - TOL) |
|||
observer[sc.DO("Product 4 Release Gear")].addEventCheck(time + 1.22 + TOL, True) |
|||
|
|||
observer[sc.DO("Product 4 Release Gear")].addNoChangeCheck(time + 2.22 - TOL) |
|||
observer[sc.DO("Product 4 Release Gear")].addEventCheck(time + 2.22 + TOL, False) |
|||
|
|||
observer[sc.DO("Product 4 Release Gear")].addNoChangeCheck(time + 2.72 - TOL) |
|||
observer[sc.DO("Product 4 Release Gear")].addEventCheck(time + 2.72 + TOL, True) |
|||
|
|||
observer[sc.DO("Product 4 Release Gear")].addNoChangeCheck(time + 3.72 - TOL) |
|||
observer[sc.DO("Product 4 Release Gear")].addEventCheck(time + 3.72 + TOL, False) |
|||
|
|||
observer[sc.DO("Product 4 Release Gear")].addNoChangeCheck(time + 4.22 - TOL) |
|||
observer[sc.DO("Product 4 Release Gear")].addEventCheck(time + 4.22 + TOL, True) |
|||
|
|||
observer[sc.DO("Open Cash Box Actor")].addNoChangeCheck(time + 5.21 - TOL) |
|||
observer[sc.DO("Open Cash Box Actor")].addEventCheck(time + 5.21 + TOL, False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 5.21 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 5.21 + TOL, True) |
|||
|
|||
observer[sc.DO("Product 4 Release Gear")].addNoChangeCheck(time + 5.22 - TOL) |
|||
observer[sc.DO("Product 4 Release Gear")].addEventCheck(time + 5.22 + TOL, False) |
|||
|
|||
observer[sc.CC("GSM Modem")].addNoChangeCheck(time + 5.23 - TOL) |
|||
observer[sc.CC("GSM Modem")].addEventCheck(time + 5.23 + TOL, bytearray(b"AT+CMGF=1\x0aAT+CMGS=\"+")) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 5.24 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 5.24 + TOL, DisplayData.fromFileContents(binaryData('4.rbb'))) |
|||
|
|||
observer[sc.CC("GSM Modem")].addNoChangeCheck(time + 5.24 - TOL) |
|||
observer[sc.CC("GSM Modem")].addEventCheck(time + 5.24 + TOL, bytearray(b"4915233767667\"\x0aSlot ")) |
|||
|
|||
observer[sc.CC("GSM Modem")].addNoChangeCheck(time + 5.25 - TOL) |
|||
observer[sc.CC("GSM Modem")].addEventCheck(time + 5.25 + TOL, bytearray(b"blocked\x1a\x0a")) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 5.72 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 5.72 + TOL, False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 6.22 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 6.22 + TOL, True) |
|||
|
|||
observer.sleep(6.486) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("Automatic light barrier").setValue(True) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 0.23 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 0.23 + TOL, False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 0.73 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 0.73 + TOL, True) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 1.23 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 1.23 + TOL, False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 1.74 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 1.74 + TOL, True) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 1.74 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 1.74 + TOL, DisplayData.fromFileContents(binaryData('0.rbb'))) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 2.24 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 2.24 + TOL, False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 2.73 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 2.73 + TOL, True) |
|||
|
|||
observer[sc.DO("Open Cash Box Actor")].addNoChangeCheck(time + 3.23 - TOL) |
|||
observer[sc.DO("Open Cash Box Actor")].addEventCheck(time + 3.23 + TOL, True) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 3.23 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 3.23 + TOL, False) |
|||
|
|||
observer.sleep(4.829) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Product 4 Button").setValue(True) |
|||
|
|||
observer[sc.DO("Product 4 Lamp")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DO("Product 4 Lamp")].addEventCheck(time + 0.02 + TOL, True) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.02 + TOL, DisplayData.fromFileContents(binaryData('5.rbb'))) |
|||
|
|||
observer.sleep(0.141) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Product 4 Button").setValue(False) |
|||
|
|||
observer.sleep(1.907) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Return Money Button").setValue(True) |
|||
|
|||
observer[sc.DO("Open Cash Box Actor")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DO("Open Cash Box Actor")].addEventCheck(time + 0.02 + TOL, False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 0.02 + TOL, True) |
|||
|
|||
observer[sc.DO("Product 4 Lamp")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DO("Product 4 Lamp")].addEventCheck(time + 0.02 + TOL, False) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.04 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.04 + TOL, DisplayData.fromFileContents(binaryData('6.rbb'))) |
|||
|
|||
observer.sleep(0.102) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Return Money Button").setValue(False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 0.43 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 0.43 + TOL, False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 0.93 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 0.93 + TOL, True) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 1.42 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 1.42 + TOL, False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 1.92 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 1.92 + TOL, True) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 2.43 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 2.43 + TOL, False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 2.92 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 2.92 + TOL, True) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 2.92 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 2.92 + TOL, DisplayData.fromFileContents(binaryData('0.rbb'))) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 3.42 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 3.42 + TOL, False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 3.92 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 3.92 + TOL, True) |
|||
|
|||
observer[sc.DO("Open Cash Box Actor")].addNoChangeCheck(time + 4.42 - TOL) |
|||
observer[sc.DO("Open Cash Box Actor")].addEventCheck(time + 4.42 + TOL, True) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 4.42 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 4.42 + TOL, False) |
|||
|
|||
observer.sleep(6.149 + TOL) |
|||
|
|||
time = observer.getTime() |
|||
|
|||
# Test end conditions |
|||
observer[sc.DO("Product 4 Lamp")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Product 3 Lamp")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Product 2 Lamp")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Product 1 Lamp")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Dispense Bay Lamp")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Open Cash Box Actor")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Cash Box Return Actor")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Product 1 Release Gear")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Product 2 Release Gear")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Product 3 Release Gear")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Product 4 Release Gear")].addNoChangeCheck(time - TOL) |
|||
observer[sc.CC("GSM Modem")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DP("Display")].addNoChangeCheck(time - TOL) |
|||
|
|||
observer.stop() |
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@ -0,0 +1,297 @@ |
|||
#!/usr/bin/python |
|||
from redBlocks import * |
|||
from redBlocksTest import * |
|||
|
|||
# This script was generated by the redBlocks Simulator's test script recorder. |
|||
# It serves for demonstration purposes and tests the workflow to buy a product. |
|||
# It needs to be started with all slots being unblocked and will leave the system with one bottle being retrieved from the second slot. |
|||
|
|||
scf = SimulatorConnectionFactory() |
|||
|
|||
# Registration of interfaces |
|||
scf.registerDO("Product 4 Lamp") |
|||
scf.registerDO("Product 3 Lamp") |
|||
scf.registerDO("Product 2 Lamp") |
|||
scf.registerDO("Product 1 Lamp") |
|||
scf.registerDO("Dispense Bay Lamp") |
|||
scf.registerDO("Change Bay Lamp") |
|||
scf.registerDO("Open Cash Box Actor") |
|||
scf.registerDO("Cash Box Return Actor") |
|||
scf.registerDO("Product 1 Release Gear") |
|||
scf.registerDO("Product 2 Release Gear") |
|||
scf.registerDO("Product 3 Release Gear") |
|||
scf.registerDO("Product 4 Release Gear") |
|||
scf.registerCC("GSM Modem") |
|||
scf.registerDP("Display") |
|||
scf.registerDI("Product 4 Button") |
|||
scf.registerDI("Product 3 Button") |
|||
scf.registerDI("Product 2 Button") |
|||
scf.registerDI("Product 1 Button") |
|||
scf.registerSBO("Euro100") |
|||
scf.registerSBO("Euro50") |
|||
scf.registerSBO("Euro20") |
|||
scf.registerSBO("Euro10") |
|||
sc = scf.create() |
|||
|
|||
# Define set of interfaces to observe |
|||
observer = Observer() |
|||
observer.add(sc.DO("Product 4 Lamp")) |
|||
observer.add(sc.DO("Product 3 Lamp")) |
|||
observer.add(sc.DO("Product 2 Lamp")) |
|||
observer.add(sc.DO("Product 1 Lamp")) |
|||
observer.add(sc.DO("Dispense Bay Lamp")) |
|||
observer.add(sc.DO("Change Bay Lamp")) |
|||
observer.add(sc.DO("Open Cash Box Actor")) |
|||
observer.add(sc.DO("Cash Box Return Actor")) |
|||
observer.add(sc.DO("Product 1 Release Gear")) |
|||
observer.add(sc.DO("Product 2 Release Gear")) |
|||
observer.add(sc.DO("Product 3 Release Gear")) |
|||
observer.add(sc.DO("Product 4 Release Gear")) |
|||
observer.add(sc.CC("GSM Modem"), 0.10) |
|||
observer.add(sc.DP("Display"), 0.10) |
|||
|
|||
# time tolerance: adjust to a suitable value depending on the latency of the test setup |
|||
TOL = 0.20 |
|||
observer.setTolerance(TOL) |
|||
|
|||
observer.start() |
|||
time = observer.getTime() |
|||
|
|||
|
|||
# Test Preconditions |
|||
observer[sc.DO("Product 4 Lamp")].checkData(False) |
|||
observer[sc.DO("Product 3 Lamp")].checkData(False) |
|||
observer[sc.DO("Product 2 Lamp")].checkData(False) |
|||
observer[sc.DO("Product 1 Lamp")].checkData(False) |
|||
observer[sc.DO("Dispense Bay Lamp")].checkData(False) |
|||
observer[sc.DO("Change Bay Lamp")].checkData(False) |
|||
observer[sc.DO("Open Cash Box Actor")].checkData(True) |
|||
observer[sc.DO("Cash Box Return Actor")].checkData(False) |
|||
observer[sc.DO("Product 1 Release Gear")].checkData(False) |
|||
observer[sc.DO("Product 2 Release Gear")].checkData(False) |
|||
observer[sc.DO("Product 3 Release Gear")].checkData(False) |
|||
observer[sc.DO("Product 4 Release Gear")].checkData(False) |
|||
observer[sc.DP("Display")].checkData(DisplayData.fromFileContents(binaryData('2.rbb'))) |
|||
|
|||
observer.sleep(1.136) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Product 4 Button").setValue(True) |
|||
|
|||
observer[sc.DO("Product 4 Lamp")].addNoChangeCheck(time + 0.01 - TOL) |
|||
observer[sc.DO("Product 4 Lamp")].addEventCheck(time + 0.01 + TOL, True) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.02 + TOL, DisplayData.fromFileContents(binaryData('3.rbb'))) |
|||
|
|||
observer.sleep(0.127) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Product 4 Button").setValue(False) |
|||
|
|||
observer.sleep(0.752) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Product 3 Button").setValue(True) |
|||
|
|||
observer[sc.DO("Product 3 Lamp")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DO("Product 3 Lamp")].addEventCheck(time + 0.02 + TOL, True) |
|||
|
|||
observer[sc.DO("Product 4 Lamp")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DO("Product 4 Lamp")].addEventCheck(time + 0.02 + TOL, False) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.02 + TOL, DisplayData.fromFileContents(binaryData('4.rbb'))) |
|||
|
|||
observer.sleep(0.096) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Product 3 Button").setValue(False) |
|||
|
|||
observer.sleep(0.715) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Product 2 Button").setValue(True) |
|||
|
|||
observer[sc.DO("Product 2 Lamp")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DO("Product 2 Lamp")].addEventCheck(time + 0.02 + TOL, True) |
|||
|
|||
observer[sc.DO("Product 3 Lamp")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DO("Product 3 Lamp")].addEventCheck(time + 0.02 + TOL, False) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.02 + TOL, DisplayData.fromFileContents(binaryData('5.rbb'))) |
|||
|
|||
observer.sleep(0.093) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Product 2 Button").setValue(False) |
|||
|
|||
observer.sleep(0.722) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Product 1 Button").setValue(True) |
|||
|
|||
observer[sc.DO("Product 1 Lamp")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DO("Product 1 Lamp")].addEventCheck(time + 0.02 + TOL, True) |
|||
|
|||
observer[sc.DO("Product 2 Lamp")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DO("Product 2 Lamp")].addEventCheck(time + 0.02 + TOL, False) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.02 + TOL, DisplayData.fromFileContents(binaryData('6.rbb'))) |
|||
|
|||
observer.sleep(0.102) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Product 1 Button").setValue(False) |
|||
|
|||
observer.sleep(0.986) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Product 3 Button").setValue(True) |
|||
|
|||
observer[sc.DO("Product 1 Lamp")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DO("Product 1 Lamp")].addEventCheck(time + 0.02 + TOL, False) |
|||
|
|||
observer[sc.DO("Product 3 Lamp")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DO("Product 3 Lamp")].addEventCheck(time + 0.02 + TOL, True) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.02 + TOL, DisplayData.fromFileContents(binaryData('4.rbb'))) |
|||
|
|||
observer.sleep(0.085) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Product 3 Button").setValue(False) |
|||
|
|||
observer.sleep(1.083) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("Euro100").setValue(True) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.03 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.03 + TOL, DisplayData.fromFileContents(binaryData('7.rbb'))) |
|||
|
|||
observer.sleep(0.094) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("Euro100").setValue(False) |
|||
|
|||
observer.sleep(0.745) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("Euro50").setValue(True) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.04 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.04 + TOL, DisplayData.fromFileContents(binaryData('8.rbb'))) |
|||
|
|||
observer.sleep(0.089) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("Euro50").setValue(False) |
|||
|
|||
observer.sleep(0.703) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("Euro20").setValue(True) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.03 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.03 + TOL, DisplayData.fromFileContents(binaryData('9.rbb'))) |
|||
|
|||
observer.sleep(0.107) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("Euro20").setValue(False) |
|||
|
|||
observer.sleep(0.753) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("Euro10").setValue(True) |
|||
|
|||
observer[sc.DO("Product 3 Release Gear")].addNoChangeCheck(time + 0.03 - TOL) |
|||
observer[sc.DO("Product 3 Release Gear")].addEventCheck(time + 0.03 + TOL, True) |
|||
|
|||
observer[sc.DO("Product 3 Lamp")].addNoChangeCheck(time + 0.03 - TOL) |
|||
observer[sc.DO("Product 3 Lamp")].addEventCheck(time + 0.03 + TOL, False) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.03 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.03 + TOL, DisplayData.fromFileContents(binaryData('10.rbb'))) |
|||
|
|||
observer.sleep(0.203) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("Euro10").setValue(False) |
|||
|
|||
observer[sc.DO("Cash Box Return Actor")].addNoChangeCheck(time + 0.82 - TOL) |
|||
observer[sc.DO("Cash Box Return Actor")].addEventCheck(time + 0.82 + TOL, True) |
|||
|
|||
observer[sc.DO("Product 3 Release Gear")].addNoChangeCheck(time + 0.83 - TOL) |
|||
observer[sc.DO("Product 3 Release Gear")].addEventCheck(time + 0.83 + TOL, False) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.83 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.83 + TOL, DisplayData.fromFileContents(binaryData('11.rbb'))) |
|||
|
|||
observer[sc.DO("Open Cash Box Actor")].addNoChangeCheck(time + 1.82 - TOL) |
|||
observer[sc.DO("Open Cash Box Actor")].addEventCheck(time + 1.82 + TOL, False) |
|||
|
|||
observer[sc.DO("Dispense Bay Lamp")].addNoChangeCheck(time + 2.32 - TOL) |
|||
observer[sc.DO("Dispense Bay Lamp")].addEventCheck(time + 2.32 + TOL, True) |
|||
|
|||
observer[sc.DO("Dispense Bay Lamp")].addNoChangeCheck(time + 2.82 - TOL) |
|||
observer[sc.DO("Dispense Bay Lamp")].addEventCheck(time + 2.82 + TOL, False) |
|||
|
|||
observer[sc.DO("Dispense Bay Lamp")].addNoChangeCheck(time + 3.32 - TOL) |
|||
observer[sc.DO("Dispense Bay Lamp")].addEventCheck(time + 3.32 + TOL, True) |
|||
|
|||
observer[sc.DO("Dispense Bay Lamp")].addNoChangeCheck(time + 3.82 - TOL) |
|||
observer[sc.DO("Dispense Bay Lamp")].addEventCheck(time + 3.82 + TOL, False) |
|||
|
|||
observer[sc.DO("Dispense Bay Lamp")].addNoChangeCheck(time + 4.32 - TOL) |
|||
observer[sc.DO("Dispense Bay Lamp")].addEventCheck(time + 4.32 + TOL, True) |
|||
|
|||
observer[sc.DO("Cash Box Return Actor")].addNoChangeCheck(time + 4.82 - TOL) |
|||
observer[sc.DO("Cash Box Return Actor")].addEventCheck(time + 4.82 + TOL, False) |
|||
|
|||
observer[sc.DO("Open Cash Box Actor")].addNoChangeCheck(time + 4.82 - TOL) |
|||
observer[sc.DO("Open Cash Box Actor")].addEventCheck(time + 4.82 + TOL, True) |
|||
|
|||
observer[sc.DO("Dispense Bay Lamp")].addNoChangeCheck(time + 4.82 - TOL) |
|||
observer[sc.DO("Dispense Bay Lamp")].addEventCheck(time + 4.82 + TOL, False) |
|||
|
|||
observer[sc.DO("Dispense Bay Lamp")].addNoChangeCheck(time + 5.33 - TOL) |
|||
observer[sc.DO("Dispense Bay Lamp")].addEventCheck(time + 5.33 + TOL, True) |
|||
|
|||
observer[sc.DO("Dispense Bay Lamp")].addNoChangeCheck(time + 5.82 - TOL) |
|||
observer[sc.DO("Dispense Bay Lamp")].addEventCheck(time + 5.82 + TOL, False) |
|||
|
|||
observer[sc.DO("Dispense Bay Lamp")].addNoChangeCheck(time + 6.32 - TOL) |
|||
observer[sc.DO("Dispense Bay Lamp")].addEventCheck(time + 6.32 + TOL, True) |
|||
|
|||
observer[sc.DO("Dispense Bay Lamp")].addNoChangeCheck(time + 6.82 - TOL) |
|||
observer[sc.DO("Dispense Bay Lamp")].addEventCheck(time + 6.82 + TOL, False) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 7.33 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 7.33 + TOL, DisplayData.fromFileContents(binaryData('2.rbb'))) |
|||
|
|||
observer.sleep(10.130 + TOL) |
|||
|
|||
time = observer.getTime() |
|||
|
|||
# Test end conditions |
|||
observer[sc.DO("Product 4 Lamp")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Product 3 Lamp")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Product 2 Lamp")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Product 1 Lamp")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Dispense Bay Lamp")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Open Cash Box Actor")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Cash Box Return Actor")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Product 1 Release Gear")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Product 2 Release Gear")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Product 3 Release Gear")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Product 4 Release Gear")].addNoChangeCheck(time - TOL) |
|||
observer[sc.CC("GSM Modem")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DP("Display")].addNoChangeCheck(time - TOL) |
|||
|
|||
observer.stop() |
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@ -0,0 +1,310 @@ |
|||
#!/usr/bin/python |
|||
from redBlocks import * |
|||
from redBlocksTest import * |
|||
|
|||
# This script was generated by the redBlocks Simulator's test script recorder. |
|||
# It serves for demonstration purposes and tests the application's behaviour when the vending machine's door is opened in order to do maintenance and fill up the slots. |
|||
# It needs to be started with the first slot being blocked and will end with all slots being unblocked. |
|||
|
|||
scf = SimulatorConnectionFactory() |
|||
|
|||
# Registration of interfaces |
|||
scf.registerDO("Product 4 Lamp") |
|||
scf.registerDO("Product 3 Lamp") |
|||
scf.registerDO("Product 2 Lamp") |
|||
scf.registerDO("Product 1 Lamp") |
|||
scf.registerDO("Dispense Bay Lamp") |
|||
scf.registerDO("Change Bay Lamp") |
|||
scf.registerDO("Open Cash Box Actor") |
|||
scf.registerDO("Cash Box Return Actor") |
|||
scf.registerDO("Product 1 Release Gear") |
|||
scf.registerDO("Product 2 Release Gear") |
|||
scf.registerDO("Product 3 Release Gear") |
|||
scf.registerDO("Product 4 Release Gear") |
|||
scf.registerCC("GSM Modem") |
|||
scf.registerDP("Display") |
|||
scf.registerDI("Product 4 Button") |
|||
scf.registerDI("Return Money Button") |
|||
scf.registerDI("Front Door Protection") |
|||
scf.registerSBO("KeyPad1") |
|||
scf.registerSBO("KeyPad2") |
|||
scf.registerSBO("KeyPad3") |
|||
scf.registerSBO("KeyPad4") |
|||
scf.registerDI("Filled Up Button") |
|||
sc = scf.create() |
|||
|
|||
# Define set of interfaces to observe |
|||
observer = Observer() |
|||
observer.add(sc.DO("Product 4 Lamp")) |
|||
observer.add(sc.DO("Product 3 Lamp")) |
|||
observer.add(sc.DO("Product 2 Lamp")) |
|||
observer.add(sc.DO("Product 1 Lamp")) |
|||
observer.add(sc.DO("Dispense Bay Lamp")) |
|||
observer.add(sc.DO("Change Bay Lamp")) |
|||
observer.add(sc.DO("Open Cash Box Actor")) |
|||
observer.add(sc.DO("Cash Box Return Actor")) |
|||
observer.add(sc.DO("Product 1 Release Gear")) |
|||
observer.add(sc.DO("Product 2 Release Gear")) |
|||
observer.add(sc.DO("Product 3 Release Gear")) |
|||
observer.add(sc.DO("Product 4 Release Gear")) |
|||
observer.add(sc.CC("GSM Modem"), 0.10) |
|||
observer.add(sc.DP("Display"), 0.10) |
|||
|
|||
# time tolerance: adjust to a suitable value depending on the latency of the test setup |
|||
TOL = 0.20 |
|||
observer.setTolerance(TOL) |
|||
|
|||
observer.start() |
|||
time = observer.getTime() |
|||
|
|||
|
|||
# Test Preconditions |
|||
observer[sc.DO("Product 4 Lamp")].checkData(False) |
|||
observer[sc.DO("Product 3 Lamp")].checkData(False) |
|||
observer[sc.DO("Product 2 Lamp")].checkData(False) |
|||
observer[sc.DO("Product 1 Lamp")].checkData(False) |
|||
observer[sc.DO("Dispense Bay Lamp")].checkData(False) |
|||
observer[sc.DO("Change Bay Lamp")].checkData(False) |
|||
observer[sc.DO("Open Cash Box Actor")].checkData(True) |
|||
observer[sc.DO("Cash Box Return Actor")].checkData(False) |
|||
observer[sc.DO("Product 1 Release Gear")].checkData(False) |
|||
observer[sc.DO("Product 2 Release Gear")].checkData(False) |
|||
observer[sc.DO("Product 3 Release Gear")].checkData(False) |
|||
observer[sc.DO("Product 4 Release Gear")].checkData(False) |
|||
observer[sc.DP("Display")].checkData(DisplayData.fromFileContents(binaryData('0.rbb'))) |
|||
|
|||
observer.sleep(0.253) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Product 4 Button").setValue(True) |
|||
|
|||
observer[sc.DO("Product 4 Lamp")].addNoChangeCheck(time + 0.05 - TOL) |
|||
observer[sc.DO("Product 4 Lamp")].addEventCheck(time + 0.05 + TOL, True) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.05 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.05 + TOL, DisplayData.fromFileContents(binaryData('1.rbb'))) |
|||
|
|||
observer.sleep(0.084) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Product 4 Button").setValue(False) |
|||
|
|||
observer.sleep(1.018) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Return Money Button").setValue(True) |
|||
|
|||
observer[sc.DO("Open Cash Box Actor")].addNoChangeCheck(time + 0.03 - TOL) |
|||
observer[sc.DO("Open Cash Box Actor")].addEventCheck(time + 0.03 + TOL, False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 0.03 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 0.03 + TOL, True) |
|||
|
|||
observer[sc.DO("Product 4 Lamp")].addNoChangeCheck(time + 0.03 - TOL) |
|||
observer[sc.DO("Product 4 Lamp")].addEventCheck(time + 0.03 + TOL, False) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.03 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.03 + TOL, DisplayData.fromFileContents(binaryData('2.rbb'))) |
|||
|
|||
observer.sleep(0.083) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Return Money Button").setValue(False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 0.45 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 0.45 + TOL, False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 0.95 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 0.95 + TOL, True) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 1.53 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 1.53 + TOL, False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 1.95 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 1.95 + TOL, True) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 2.45 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 2.45 + TOL, False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 2.95 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 2.95 + TOL, True) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 2.95 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 2.95 + TOL, DisplayData.fromFileContents(binaryData('0.rbb'))) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 3.45 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 3.45 + TOL, False) |
|||
|
|||
observer.sleep(3.566) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Front Door Protection").setValue(False) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.03 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.03 + TOL, DisplayData.fromFileContents(binaryData('3.rbb'))) |
|||
|
|||
observer.sleep(1.571) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("KeyPad1").setValue(True) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.05 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.05 + TOL, DisplayData.fromFileContents(binaryData('4.rbb'))) |
|||
|
|||
observer.sleep(0.363) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("KeyPad1").setValue(False) |
|||
|
|||
observer.sleep(0.601) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("KeyPad2").setValue(True) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.07 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.07 + TOL, DisplayData.fromFileContents(binaryData('5.rbb'))) |
|||
|
|||
observer.sleep(0.352) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("KeyPad2").setValue(False) |
|||
|
|||
observer.sleep(0.702) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("KeyPad3").setValue(True) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.07 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.07 + TOL, DisplayData.fromFileContents(binaryData('6.rbb'))) |
|||
|
|||
observer.sleep(0.316) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("KeyPad3").setValue(False) |
|||
|
|||
observer.sleep(0.684) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("KeyPad4").setValue(True) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.07 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.07 + TOL, DisplayData.fromFileContents(binaryData('7.rbb'))) |
|||
|
|||
observer.sleep(0.332) |
|||
|
|||
time = observer.getTime() |
|||
sc.SBO("KeyPad4").setValue(False) |
|||
|
|||
observer.sleep(0.838) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Filled Up Button").setValue(True) |
|||
|
|||
observer.sleep(0.385) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Filled Up Button").setValue(False) |
|||
|
|||
observer.sleep(1.502) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Front Door Protection").setValue(True) |
|||
|
|||
observer[sc.DO("Open Cash Box Actor")].addNoChangeCheck(time + 0.03 - TOL) |
|||
observer[sc.DO("Open Cash Box Actor")].addEventCheck(time + 0.03 + TOL, True) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.03 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.03 + TOL, DisplayData.fromFileContents(binaryData('0.rbb'))) |
|||
|
|||
observer.sleep(1.217) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Product 4 Button").setValue(True) |
|||
|
|||
observer[sc.DO("Product 4 Lamp")].addNoChangeCheck(time + 0.03 - TOL) |
|||
observer[sc.DO("Product 4 Lamp")].addEventCheck(time + 0.03 + TOL, True) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.05 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.05 + TOL, DisplayData.fromFileContents(binaryData('8.rbb'))) |
|||
|
|||
observer.sleep(0.247) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Product 4 Button").setValue(False) |
|||
|
|||
observer.sleep(1.038) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Return Money Button").setValue(True) |
|||
|
|||
observer[sc.DO("Open Cash Box Actor")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DO("Open Cash Box Actor")].addEventCheck(time + 0.02 + TOL, False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 0.02 + TOL, True) |
|||
|
|||
observer[sc.DO("Product 4 Lamp")].addNoChangeCheck(time + 0.02 - TOL) |
|||
observer[sc.DO("Product 4 Lamp")].addEventCheck(time + 0.02 + TOL, False) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 0.03 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 0.03 + TOL, DisplayData.fromFileContents(binaryData('2.rbb'))) |
|||
|
|||
observer.sleep(0.279) |
|||
|
|||
time = observer.getTime() |
|||
sc.DI("Return Money Button").setValue(False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 0.25 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 0.25 + TOL, False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 0.75 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 0.75 + TOL, True) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 1.25 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 1.25 + TOL, False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 1.75 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 1.75 + TOL, True) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 2.25 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 2.25 + TOL, False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 2.75 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 2.75 + TOL, True) |
|||
|
|||
observer[sc.DP("Display")].addNoChangeCheck(time + 2.75 - TOL) |
|||
observer[sc.DP("Display")].addEventCheck(time + 2.75 + TOL, DisplayData.fromFileContents(binaryData('0.rbb'))) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 3.26 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 3.26 + TOL, False) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 3.76 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 3.76 + TOL, True) |
|||
|
|||
observer[sc.DO("Open Cash Box Actor")].addNoChangeCheck(time + 4.26 - TOL) |
|||
observer[sc.DO("Open Cash Box Actor")].addEventCheck(time + 4.26 + TOL, True) |
|||
|
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time + 4.26 - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addEventCheck(time + 4.26 + TOL, False) |
|||
|
|||
observer.sleep(5.141 + TOL) |
|||
|
|||
time = observer.getTime() |
|||
|
|||
# Test end conditions |
|||
observer[sc.DO("Product 4 Lamp")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Product 3 Lamp")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Product 2 Lamp")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Product 1 Lamp")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Dispense Bay Lamp")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Change Bay Lamp")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Open Cash Box Actor")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Cash Box Return Actor")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Product 1 Release Gear")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Product 2 Release Gear")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Product 3 Release Gear")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DO("Product 4 Release Gear")].addNoChangeCheck(time - TOL) |
|||
observer[sc.CC("GSM Modem")].addNoChangeCheck(time - TOL) |
|||
observer[sc.DP("Display")].addNoChangeCheck(time - TOL, [0, 0, 128, 64]) |
|||
|
|||
observer.stop() |
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@ -0,0 +1,21 @@ |
|||
#!/usr/bin/python |
|||
from redBlocksTestSuite import * |
|||
|
|||
# This test suite tests the normal workflow, which includes buying a product, |
|||
# simulating a jammed slot and resetting the slot by entering maintenance mode. |
|||
|
|||
s = Simulator("../../VendingMachine.rbp", "-c tcp:10000") |
|||
s.startAfterSimulation("runBinary.bat") |
|||
|
|||
t = TestSuite(s, r"results\result.txt", "logs") |
|||
# Test the normal product buying workflow. |
|||
t.addTest(r"Buy_Product_Test.py") |
|||
t.beginTestSequence() |
|||
# Simulate a blocked product slot 4. |
|||
t.addTest(r"Blocked_Slot_Test.py") |
|||
# Clear blocked slot during maintenance. |
|||
t.addTest(r"Maintenance_Mode_Test.py") |
|||
# Repeat the normal buying workflow test, in order to check whether the cleard slot is handled normally. |
|||
t.addTest(r"Buy_Product_Test.py", "Buy_Product_Via_Cleared_Slot_Test") |
|||
t.endTestSequence() |
|||
t.run() |
@ -0,0 +1 @@ |
|||
Autonomous test execution is not supported by the evaluation version! |
@ -0,0 +1,23 @@ |
|||
# Defines a list of additional include directories that will be prepended to the list of |
|||
# standard include directories. |
|||
INCLUDE_DIRS = \ |
|||
$(REL_SRC_DIR) \ |
|||
$(REL_PROJECT_DIR)/sim \ |
|||
$(REL_PROJECT_DIR)/sim/host/Workbench |
|||
|
|||
# Defines a list of directories which are searched for source files recursively. |
|||
# All source files found within these directories are compiled and linked to the binary. |
|||
SOURCES_DIRS_RECURSIVE = \ |
|||
$(REL_SRC_DIR) \ |
|||
$(REL_PROJECT_DIR)/sim/host/Workbench |
|||
|
|||
# Defines a list of directories which are searched for source files non-recursively. |
|||
# All source files found within these directories are compiled and linked to the binary. |
|||
SOURCES_DIRS = \ |
|||
$(REL_PROJECT_DIR)/sim |
|||
|
|||
# Defines a list of source files which should be removed from the list of sources. |
|||
SOURCES_EXCLUDES = |
|||
|
|||
# Defines a list of source files which should be added to the list of sources. |
|||
SOURCES_INCLUDES = |
@ -0,0 +1,40 @@ |
|||
#include "AlarmManager.h" |
|||
#include "Platform.h" |
|||
|
|||
|
|||
static const char* const alarmMessages[] = |
|||
{ |
|||
"Break-in attempt", |
|||
"Overheat", |
|||
"Slot empty", |
|||
"Slot blocked" |
|||
}; |
|||
|
|||
static const char* const number = "+4915233767667"; |
|||
|
|||
|
|||
AlarmManager::AlarmManager() : |
|||
mAlarmEvent( this ), |
|||
mAlarms( 0 ) |
|||
{ |
|||
} |
|||
|
|||
void AlarmManager::raiseAlarm( Alarm alarm ) |
|||
{ |
|||
AlarmManager& instance = getInstanceRef(); |
|||
instance.mAlarms |= 1u << static_cast<u8>( alarm ); |
|||
instance.mAlarmEvent.schedule(); |
|||
} |
|||
|
|||
void AlarmManager::onAlarmEvent( ThisType* t, u8 callCnt ) |
|||
{ |
|||
redBlocks::unused( callCnt ); |
|||
for ( u8 i = 0; i < sizeof( alarmMessages ) / sizeof( const char* ); ++i ) |
|||
{ |
|||
if ( 0 != ( t->mAlarms & ( 1u << i ) ) ) |
|||
{ |
|||
Platform::GsmModemDriver::sendSms( number, alarmMessages[i] ); |
|||
} |
|||
} |
|||
t->mAlarms = 0; |
|||
} |
@ -0,0 +1,47 @@ |
|||
#ifndef ALARM_MANAGER_H_ |
|||
#define ALARM_MANAGER_H_ |
|||
|
|||
#include "Platform.h" |
|||
#include <Core/Base/TGlobalPtrBase.h> |
|||
|
|||
/**
|
|||
* This class deals with all alarm messages, sending an SMS via |
|||
* the GSM modem. |
|||
*/ |
|||
class AlarmManager : public redBlocks::Core::TGlobalPtrBase<AlarmManager> |
|||
{ |
|||
public: |
|||
enum Alarm |
|||
{ |
|||
ALARM_BREAK_IN = 0, |
|||
ALARM_OVERHEAT, |
|||
ALARM_EMPTY_SLOT, |
|||
ALARM_SLOT_BLOCKED |
|||
}; |
|||
|
|||
/**
|
|||
* Constructor |
|||
*/ |
|||
AlarmManager(); |
|||
|
|||
/**
|
|||
* Raises the specified alarm. This method can be called from interrupt |
|||
* context, as is only sets a flag and schedules an Event |
|||
* @param alarm the alarm to raise |
|||
*/ |
|||
static void raiseAlarm( Alarm alarm ); |
|||
|
|||
private: |
|||
/** Convenience definition for our class */ |
|||
typedef AlarmManager ThisType; |
|||
/**
|
|||
* This method is associated with mAlarmEvent |
|||
*/ |
|||
static void onAlarmEvent( ThisType* t, u8 callCnt ); |
|||
/** this event is scheduled by raiseAlarm() */ |
|||
Platform::OS::TEvent<ThisType, &onAlarmEvent> mAlarmEvent; |
|||
/** bit field of active alarms */ |
|||
u32 mAlarms; |
|||
}; |
|||
|
|||
#endif |
@ -0,0 +1,40 @@ |
|||
#include "Application.h" |
|||
#include "Gui/Gui.h" |
|||
|
|||
|
|||
Application::Application() : |
|||
mTemperatureControllerTimer( this ), |
|||
// cooling temperature 8 +/- 2 degrees, alarm at 14 degrees
|
|||
mTemperatureController( 8000, 2000, 14000 ), |
|||
mVendingMode(), |
|||
mGlobalState( mVendingMode, mMaintenanceMode ) |
|||
{ |
|||
Platform::PowerSupervision::enableCallback(); |
|||
Platform::LightBarrier::enableCallback(); |
|||
Platform::FrontDoorProtection::enableCallback(); |
|||
Platform::ReturnMoneyButton::enableCallback(); |
|||
Platform::FilledUpButton::enableCallback(); |
|||
Platform::Product1Button::enableCallback(); |
|||
Platform::Product2Button::enableCallback(); |
|||
Platform::Product3Button::enableCallback(); |
|||
Platform::Product4Button::enableCallback(); |
|||
Platform::StartButton::enableCallback(); |
|||
Platform::TemperatureSensor::enableCallback(); |
|||
mTemperatureControllerTimer.startPeriodic( Platform::OS::MilliSec<100>::value ); |
|||
} |
|||
|
|||
void Application::run() const |
|||
{ |
|||
for( ;; ) |
|||
{ |
|||
Platform::OS::processEvents(); |
|||
Platform::enterSleepMode(); |
|||
} |
|||
} |
|||
|
|||
void Application::onTemperatureControllerTimerEvent( ThisType* t, u8 callCnt ) |
|||
{ |
|||
redBlocks::unused( callCnt ); |
|||
t->mTemperatureController.runOnce(); |
|||
} |
|||
|
@ -0,0 +1,67 @@ |
|||
#ifndef APPLICATION_H_ |
|||
#define APPLICATION_H_ |
|||
|
|||
#include "Platform.h" |
|||
#include "CashBox.h" |
|||
#include "MaintenanceMode.h" |
|||
#include "VendingMode.h" |
|||
#include "GlobalState.h" |
|||
#include "TTemperatureController.h" |
|||
#include "AlarmManager.h" |
|||
#include <Gui/Gui.h> |
|||
#include <Drivers/TTemperatureSensor.h> |
|||
#include <Core/Base/TGlobalPtrBase.h> |
|||
#include <Core/Log/Log.h> |
|||
|
|||
/**
|
|||
* Example application that provides the functionality: Each time an input |
|||
* changes, the output in 100 ms steps. |
|||
*/ |
|||
class Application: public redBlocks::Core::TGlobalPtrBase<Application> |
|||
{ |
|||
public: |
|||
typedef TTemperatureController<TTemperatureSensor<Platform::TemperatureSensor>, Platform::CoolingSystemActor> TemperatureController; |
|||
|
|||
|
|||
Application(); |
|||
|
|||
void run() const; |
|||
|
|||
static MaintenanceMode& getMaintenanceMode() |
|||
{ |
|||
return getInstanceRef().mMaintenanceMode; |
|||
} |
|||
|
|||
static VendingMode& getVendingMode() |
|||
{ |
|||
return getInstanceRef().mVendingMode; |
|||
} |
|||
|
|||
static TemperatureController& getTemperatureController() |
|||
{ |
|||
return getInstanceRef().mTemperatureController; |
|||
} |
|||
|
|||
static GlobalState& getGlobalState() |
|||
{ |
|||
return getInstanceRef().mGlobalState; |
|||
} |
|||
|
|||
private: |
|||
/** Convenience definition for our class */ |
|||
typedef Application ThisType; |
|||
|
|||
/** This method is associated with mTemperatureControllerTimer */ |
|||
static void onTemperatureControllerTimerEvent( ThisType* t, u8 callCnt ); |
|||
/** used to periodically invoke the temperature controller */ |
|||
Platform::OS::TEventTimer<ThisType, &onTemperatureControllerTimerEvent> mTemperatureControllerTimer; |
|||
|
|||
GuiResources mGuiResources; |
|||
AlarmManager mAlarmManager; |
|||
MaintenanceMode mMaintenanceMode; |
|||
TemperatureController mTemperatureController; |
|||
VendingMode mVendingMode; |
|||
GlobalState mGlobalState; |
|||
}; |
|||
|
|||
#endif // APPLICATION_H_
|
@ -0,0 +1,107 @@ |
|||
#include "CashBox.h" |
|||
#include <Core/Log/Log.h> |
|||
|
|||
CashBox::CashBox() : |
|||
mTimer( this ) |
|||
{ |
|||
mIsActive = false; |
|||
mMoneyInIntermediateCash = 0; |
|||
mState = STATE_IDLE; |
|||
mStateCounter = 0; |
|||
} |
|||
|
|||
void CashBox::setActivationState( bool isActivated ) |
|||
{ |
|||
if ( !isActivated ) |
|||
{ |
|||
mTimer.stop(); |
|||
Platform::CashBoxReturnActor::setOutput( false ); |
|||
Platform::ChangeBayLamp::setOutput( false ); |
|||
mMoneyInIntermediateCash = 0; |
|||
mState = STATE_IDLE; |
|||
} |
|||
mIsActive = isActivated; |
|||
Platform::OpenCashBoxActor::setOutput( isActivated ); |
|||
} |
|||
|
|||
void CashBox::onMoneyInserted( u16 money ) |
|||
{ |
|||
if ( mIsActive && ( mState == STATE_IDLE ) ) |
|||
{ |
|||
mMoneyInIntermediateCash += money; |
|||
RB_LOG_DEBUG( "Money inserted: " << money << " cent" ); |
|||
} |
|||
} |
|||
|
|||
void CashBox::releaseMoney() |
|||
{ |
|||
if ( mIsActive ) |
|||
{ |
|||
startReleaseMoney(); |
|||
} |
|||
} |
|||
|
|||
void CashBox::boxMoney() |
|||
{ |
|||
if ( mIsActive ) |
|||
{ |
|||
startBoxMoney(); |
|||
} |
|||
} |
|||
|
|||
|
|||
void CashBox::onTimerEvent( ThisType* t, u8 callCnt ) |
|||
{ |
|||
redBlocks::unused( callCnt ); |
|||
if ( t->mIsActive ) |
|||
{ |
|||
switch ( t->mState ) |
|||
{ |
|||
case STATE_RELEASE_MONEY: |
|||
++t->mStateCounter; |
|||
Platform::ChangeBayLamp::setOutput( 0 == t->mStateCounter % 2 ); |
|||
if ( 9 == t->mStateCounter ) |
|||
{ |
|||
t->mTimer.stop(); |
|||
Platform::OpenCashBoxActor::setOutput( true ); |
|||
t->mState = STATE_IDLE; |
|||
} |
|||
break; |
|||
case STATE_BOX_MONEY1: |
|||
Platform::OpenCashBoxActor::setOutput( false ); |
|||
t->mTimer.start( Platform::OS::Sec<3>::value ); |
|||
t->mState = STATE_BOX_MONEY2; |
|||
break; |
|||
case STATE_BOX_MONEY2: |
|||
Platform::OpenCashBoxActor::setOutput( true ); |
|||
Platform::CashBoxReturnActor::setOutput( false ); |
|||
t->mState = STATE_IDLE; |
|||
break; |
|||
case STATE_IDLE: |
|||
default: |
|||
break; |
|||
} |
|||
} |
|||
} |
|||
|
|||
void CashBox::startReleaseMoney() |
|||
{ |
|||
RB_LOG_DEBUG( "Releasing money" ); |
|||
mMoneyInIntermediateCash = 0; |
|||
|
|||
Platform::OpenCashBoxActor::setOutput( false ); |
|||
Platform::ChangeBayLamp::setOutput( true ); |
|||
mTimer.startPeriodic( Platform::OS::MilliSec<500>::value ); |
|||
mState = STATE_RELEASE_MONEY; |
|||
mStateCounter = 0; |
|||
} |
|||
|
|||
void CashBox::startBoxMoney() |
|||
{ |
|||
RB_LOG_DEBUG( "Boxing money: " << mMoneyInIntermediateCash << " cent" ) |
|||
mMoneyInIntermediateCash = 0; |
|||
|
|||
Platform::CashBoxReturnActor::setOutput( true ); |
|||
mTimer.start( Platform::OS::Sec<1>::value ); |
|||
mState = STATE_BOX_MONEY1; |
|||
} |
@ -0,0 +1,99 @@ |
|||
#ifndef CASH_BOX_H_ |
|||
#define CASH_BOX_H_ |
|||
|
|||
#include <Platform.h> |
|||
#include <Core/Base/IBase.h> |
|||
#include <Core/Base/NoCopyBase.h> |
|||
|
|||
/**
|
|||
* This class maintains the cash box, i. e. it controls the cash box flaps |
|||
* and it must be informed when a coin is inserted. |
|||
*/ |
|||
class CashBox : public redBlocks::Core::NoCopyBase |
|||
{ |
|||
public: |
|||
|
|||
/**
|
|||
* Constructor |
|||
*/ |
|||
CashBox(); |
|||
|
|||
/**
|
|||
* Activate / deactivate the cash box (if deactivated, the release flap is opened, so |
|||
* all money is falling through). |
|||
* @param isActivated true, if the cash box is active |
|||
*/ |
|||
void setActivationState( bool isActivated ); |
|||
|
|||
/**
|
|||
* Needs to be called, when money was inserted |
|||
*/ |
|||
void onMoneyInserted( u16 money ); |
|||
|
|||
/**
|
|||
* Opens the cash box release flap and switches on the return bay lamp |
|||
*/ |
|||
void releaseMoney(); |
|||
|
|||
/**
|
|||
* Boxes the money |
|||
*/ |
|||
void boxMoney(); |
|||
|
|||
/**
|
|||
* Returns the information, if a workflow is currently in progress |
|||
*/ |
|||
bool isMoneyWorkflowInProgress() const |
|||
{ |
|||
return mState != STATE_IDLE; |
|||
} |
|||
|
|||
/**
|
|||
* Returns the information, how much money is in the intermediate cash |
|||
*/ |
|||
u16 getMoneyInIntermediateCash() const |
|||
{ |
|||
return mMoneyInIntermediateCash; |
|||
} |
|||
|
|||
private: |
|||
/** Convenience definition for our class */ |
|||
typedef CashBox ThisType; |
|||
/**
|
|||
* The internal workflow state |
|||
*/ |
|||
enum State |
|||
{ |
|||
STATE_IDLE = 0, |
|||
STATE_RELEASE_MONEY, |
|||
STATE_BOX_MONEY1, |
|||
STATE_BOX_MONEY2 |
|||
}; |
|||
/**
|
|||
* This method gets called, when the timer fires. |
|||
*/ |
|||
static void onTimerEvent( ThisType* t, u8 callCnt ); |
|||
|
|||
/**
|
|||
* Releases the money |
|||
*/ |
|||
void startReleaseMoney(); |
|||
|
|||
/**
|
|||
* Boxes the money |
|||
*/ |
|||
void startBoxMoney(); |
|||
|
|||
/** used to invoke the method onTimerEvent after certain time periods */ |
|||
Platform::OS::TEventTimer<ThisType, &onTimerEvent> mTimer; |
|||
/** true, if the cash box is active */ |
|||
bool mIsActive; |
|||
/** the money that is in the intermediate cash box in cent */ |
|||
u16 mMoneyInIntermediateCash; |
|||
/** the current workflow state */ |
|||
State mState; |
|||
/** the counter that is used in certain substates */ |
|||
u8 mStateCounter; |
|||
}; |
|||
|
|||
#endif // CASH_BOX_H_
|
@ -0,0 +1,20 @@ |
|||
#include "GlobalState.h" |
|||
|
|||
|
|||
GlobalState::GlobalState( VendingMode& vendingMode, MaintenanceMode& maintenanceMode ) : |
|||
mDoorOpenEvent( this ), |
|||
mDoorCloseEvent( this ), |
|||
mVendingMode( vendingMode ), |
|||
mMaintenanceMode( maintenanceMode ) |
|||
{ |
|||
if ( Platform::FrontDoorProtection::getValue() ) |
|||
{ |
|||
mState = &mVendingState; |
|||
mVendingMode.enter(); |
|||
} |
|||
else |
|||
{ |
|||
mState = &mMaintenanceState; |
|||
mMaintenanceMode.enter(); |
|||
} |
|||
} |
@ -0,0 +1,123 @@ |
|||
#ifndef GLOBAL_STATE_H_ |
|||
#define GLOBAL_STATE_H_ |
|||
|
|||
#include "Platform.h" |
|||
#include <Core/Base/NoCopyBase.h> |
|||
#include "VendingMode.h" |
|||
#include "MaintenanceMode.h" |
|||
|
|||
/**
|
|||
* This class keeps track of the application's global state. |
|||
* It is an example of the state design pattern implementation. |
|||
*/ |
|||
class GlobalState : public redBlocks::Core::NoCopyBase |
|||
{ |
|||
private: |
|||
/** Convenience definition for our class */ |
|||
typedef GlobalState ThisType; |
|||
|
|||
|
|||
/**
|
|||
* Base class for all states: It defines a method for each trigger and |
|||
* provides default implementations for all these methods that do nothing. |
|||
*/ |
|||
class BaseState : public redBlocks::Core::NoCopyBase |
|||
{ |
|||
public: |
|||
virtual void onDoorOpen( GlobalState& context ) |
|||
{ |
|||
// do nothing per default
|
|||
} |
|||
virtual void onDoorClose( GlobalState& context ) |
|||
{ |
|||
// do nothing per default
|
|||
} |
|||
}; |
|||
|
|||
|
|||
/**
|
|||
* State class that overwrites the trigger's default behavior (i. e. do nothing) |
|||
* for the vending state. |
|||
*/ |
|||
class VendingState : public BaseState |
|||
{ |
|||
public: |
|||
virtual void onDoorOpen( GlobalState& context ) |
|||
{ |
|||
context.mVendingMode.leaveImmediate(); |
|||
context.mState = &context.mMaintenanceState; |
|||
context.mMaintenanceMode.enter(); |
|||
} |
|||
}; |
|||
friend class VendingState; |
|||
|
|||
/**
|
|||
* State class that overwrites the trigger's default behavior (i. e. do nothing) |
|||
* for the maintenance state. |
|||
*/ |
|||
class MaintenanceState : public BaseState |
|||
{ |
|||
public: |
|||
virtual void onDoorClose( GlobalState& context ) |
|||
{ |
|||
if ( context.mMaintenanceMode.leave() ) |
|||
{ |
|||
context.mState = &context.mVendingState; |
|||
context.mVendingMode.enter(); |
|||
} |
|||
} |
|||
}; |
|||
friend class MaintenanceState; |
|||
|
|||
public: |
|||
/**
|
|||
* Constructor |
|||
*/ |
|||
GlobalState( VendingMode& vendingMode, MaintenanceMode& maintenanceMode ); |
|||
|
|||
/**
|
|||
* This method must be called, when the front door changes. |
|||
* It generates an event |
|||
*/ |
|||
void onFrontDoorContactChange() |
|||
{ |
|||
if ( Platform::FrontDoorProtection::getValue() ) |
|||
{ |
|||
mDoorCloseEvent.schedule(); |
|||
} |
|||
else |
|||
{ |
|||
mDoorOpenEvent.schedule(); |
|||
} |
|||
} |
|||
|
|||
private: |
|||
/** This method is called from mDoorOpenEvent */ |
|||
static void onDoorOpenEvent( ThisType* t, u8 callCnt ) |
|||
{ |
|||
t->mState->onDoorOpen( *t ); |
|||
} |
|||
|
|||
/** This method is called from mDoorCloseEvent */ |
|||
static void onDoorCloseEvent( ThisType* t, u8 callCnt ) |
|||
{ |
|||
t->mState->onDoorClose( *t ); |
|||
} |
|||
|
|||
/** event that is scheduled, when the door is opened */ |
|||
Platform::OS::TEvent<ThisType, &onDoorOpenEvent> mDoorOpenEvent; |
|||
/** event that is scheduled, when the door is closed */ |
|||
Platform::OS::TEvent<ThisType, &onDoorCloseEvent> mDoorCloseEvent; |
|||
/** the current state */ |
|||
BaseState* mState; |
|||
/** the state object for the vending state */ |
|||
VendingState mVendingState; |
|||
/** the state object for the vending state */ |
|||
MaintenanceState mMaintenanceState; |
|||
/** reference to the vending mode state machine */ |
|||
VendingMode& mVendingMode; |
|||
/** reference to the maintenance mode state machine */ |
|||
MaintenanceMode& mMaintenanceMode; |
|||
}; |
|||
|
|||
#endif |
@ -0,0 +1,171 @@ |
|||
#include "MaintenanceMode.h" |
|||
#include "AlarmManager.h" |
|||
#include "Platform.h" |
|||
#include <Gui/MaintenanceScreen.h> |
|||
|
|||
#include <Core/Log/Log.h> |
|||
|
|||
static const Platform::OS::TimeIntervalType LAMP_TIME_INTERVAL_ALARM = Platform::OS::MilliSec<200>::value; |
|||
static const Platform::OS::TimeIntervalType LAMP_TIME_INTERVAL_STEP = Platform::OS::MilliSec<250>::value; |
|||
static const Platform::OS::TimeIntervalType LAMP_TIME_INTERVAL_MAX = Platform::OS::MilliSec<1000>::value; |
|||
static const Platform::OS::TimeIntervalType ALARM_TIME_INTERVAL = Platform::OS::Sec<5>::value; |
|||
|
|||
static const Platform::OS::TimeIntervalType SOUND_TIME_INTERVAL_CONFIRM_KEY = Platform::OS::MilliSec<300>::value; |
|||
static const Platform::OS::TimeIntervalType SOUND_TIME_INTERVAL_ERROR = Platform::OS::MilliSec<200>::value; |
|||
static const Platform::OS::TimeIntervalType SOUND_TIME_INTERVAL_CONFIRM_CODE = Platform::OS::MilliSec<1000>::value; |
|||
|
|||
|
|||
MaintenanceMode::MaintenanceMode() : |
|||
mSoundTimer( this ), |
|||
mCountdownTimer( this ), |
|||
mKeyPressedEvent( this ), |
|||
mKeyPressed( 0 ), |
|||
mAlarmState( ALARM_STATE_IDLE ), |
|||
mAlarmStateCounter( 0 ), |
|||
mKeyCodeState( KEY_CODE_STATE_IGNORE ), |
|||
mKeyCodeStateCount( 0 ), |
|||
mLampFlasher( LAMP_TIME_INTERVAL_MAX ) |
|||
{ |
|||
} |
|||
|
|||
void MaintenanceMode::enter() |
|||
{ |
|||
// this event is only relevant for the state ALARM_STATE_IDLE
|
|||
if ( mAlarmState == ALARM_STATE_IDLE ) |
|||
{ |
|||
mAlarmStateCounter = 0; |
|||
mAlarmState = ALARM_STATE_KEYCODE; |
|||
mCountdownTimer.start( ALARM_TIME_INTERVAL ); |
|||
|
|||
// let the lamp flash
|
|||
mLampFlasher.setFlashInterval( LAMP_TIME_INTERVAL_MAX ); |
|||
mLampFlasher.startFlashing( true ); |
|||
|
|||
mKeyCodeState = KEY_CODE_STATE_INPUT; |
|||
mKeyCodeStateCount = 0; |
|||
|
|||
MaintenanceScreen::drawAlarmCodePromptMessage( 0 ); |
|||
} |
|||
} |
|||
|
|||
bool MaintenanceMode::leave() |
|||
{ |
|||
bool retval = false; |
|||
if ( mAlarmState == ALARM_STATE_ACCESS_GRANTED ) |
|||
{ |
|||
mAlarmState = ALARM_STATE_IDLE; |
|||
// switch off the lamp
|
|||
mLampFlasher.setOutput( false ); |
|||
|
|||
retval = true; |
|||
} |
|||
return retval; |
|||
} |
|||
|
|||
void MaintenanceMode::onCountdownTimerEvent( ThisType* t, u8 callCnt ) |
|||
{ |
|||
redBlocks::unused( callCnt ); |
|||
// this event is only relevant for the state ALARM_STATE_KEYCODE
|
|||
if ( t->mAlarmState == ALARM_STATE_KEYCODE ) |
|||
{ |
|||
// the timer may fire three times
|
|||
if ( 3 > t->mAlarmStateCounter ) |
|||
{ |
|||
++t->mAlarmStateCounter; |
|||
// restart the countdown timer
|
|||
t->mCountdownTimer.start( ALARM_TIME_INTERVAL ); |
|||
|
|||
// accelerate the lamp flashing
|
|||
t->mLampFlasher.setFlashInterval( t->mLampFlasher.getFlashInterval() - LAMP_TIME_INTERVAL_STEP ); |
|||
} |
|||
// when the timer fires for the fourth time, we enter the alarm state
|
|||
else |
|||
{ |
|||
t->mAlarmState = ALARM_STATE_ALARM; |
|||
// raise an alarm message
|
|||
AlarmManager::raiseAlarm( AlarmManager::ALARM_BREAK_IN ); |
|||
|
|||
// let the lamp flash with the alarm flash interval
|
|||
t->mLampFlasher.setFlashInterval( LAMP_TIME_INTERVAL_ALARM ); |
|||
} |
|||
} |
|||
} |
|||
|
|||
|
|||
void MaintenanceMode::onKeyPressedEvent( ThisType* t, u8 callCnt ) |
|||
{ |
|||
redBlocks::unused( callCnt ); |
|||
// ignore the key, if we do not expect it to be pressed
|
|||
if ( KEY_CODE_STATE_INPUT == t->mKeyCodeState ) |
|||
{ |
|||
RB_LOG_DEBUG( "Key pressed: " << RB_LOG_CHAR( '0' + static_cast<char>( t->mKeyPressed ) ) ); |
|||
// store the pressed key
|
|||
t->mKeyCode[t->mKeyCodeStateCount] = t->mKeyPressed; |
|||
++t->mKeyCodeStateCount; |
|||
|
|||
// if the code is complete, we need to check it
|
|||
if ( t->mKeyCodeStateCount == sizeof( t->mKeyCode ) ) |
|||
{ |
|||
if ( t->checkKeyCode() ) |
|||
{ |
|||
RB_LOG_DEBUG( "Keycode valid" ); |
|||
MaintenanceScreen::drawMaintenanceModeMessage(); |
|||
|
|||
t->mAlarmState = ALARM_STATE_ACCESS_GRANTED; |
|||
// switch on the lamp permanently
|
|||
t->mLampFlasher.setOutput( true ); |
|||
Platform::KeySound::setOutput( true ); |
|||
|
|||
t->mKeyCodeState = KEY_CODE_STATE_CONFIRM_CODE_BEEP; |
|||
t->mSoundTimer.start( SOUND_TIME_INTERVAL_CONFIRM_CODE ); |
|||
} |
|||
else |
|||
{ |
|||
RB_LOG_DEBUG( "Keycode invalid" ); |
|||
MaintenanceScreen::drawAlarmCodePromptMessage( 0 ); |
|||
Platform::KeySound::setOutput( true ); |
|||
t->mKeyCodeState = KEY_CODE_STATE_ERROR_BEEP; |
|||
t->mKeyCodeStateCount = 0; |
|||
t->mSoundTimer.startPeriodic( SOUND_TIME_INTERVAL_ERROR ); |
|||
} |
|||
} |
|||
else |
|||
{ |
|||
MaintenanceScreen::drawAlarmCodePromptMessage( t->mKeyCodeStateCount ); |
|||
t->mKeyCodeState = KEY_CODE_STATE_CONFIRM_KEY_BEEP; |
|||
t->mSoundTimer.start( SOUND_TIME_INTERVAL_CONFIRM_KEY ); |
|||
Platform::KeySound::setOutput( true ); |
|||
} |
|||
} |
|||
} |
|||
|
|||
void MaintenanceMode::onSoundTimerEvent( ThisType* t ) |
|||
{ |
|||
RB_LOG_DEBUG( "Sound timer event fired" ); |
|||
if ( KEY_CODE_STATE_ERROR_BEEP == t->mKeyCodeState ) |
|||
{ |
|||
++t->mKeyCodeStateCount; |
|||
Platform::KeySound::setOutput( 0 == ( t->mKeyCodeStateCount % 2 ) ); |
|||
if ( 5 == t->mKeyCodeStateCount ) |
|||
{ |
|||
t->mSoundTimer.stop(); |
|||
t->mKeyCodeState = KEY_CODE_STATE_INPUT; |
|||
t->mKeyCodeStateCount = 0; |
|||
} |
|||
} |
|||
else if ( KEY_CODE_STATE_CONFIRM_KEY_BEEP == t->mKeyCodeState ) |
|||
{ |
|||
Platform::KeySound::setOutput( false ); |
|||
t->mKeyCodeState = KEY_CODE_STATE_INPUT; |
|||
} |
|||
else if ( KEY_CODE_STATE_CONFIRM_CODE_BEEP == t->mKeyCodeState ) |
|||
{ |
|||
Platform::KeySound::setOutput( false ); |
|||
t->mKeyCodeState = KEY_CODE_STATE_IGNORE; |
|||
} |
|||
} |
|||
|
|||
bool MaintenanceMode::checkKeyCode() const |
|||
{ |
|||
return 0 == memcmp( mKeyCode, "\001\002\003\004", sizeof( mKeyCode ) ); |
|||
} |
@ -0,0 +1,114 @@ |
|||
#ifndef MAINTENANCE_MODE_H_ |
|||
#define MAINTENANCE_MODE_H_ |
|||
|
|||
#include "Platform.h" |
|||
|
|||
#include <Core/Base/NoCopyBase.h> |
|||
#include <HAL/TDigitalOutputFlasher.h> |
|||
|
|||
/**
|
|||
* This class handles the alarm mechanism when entering the maintenance mode. |
|||
* Upon entering the maintenance mode, the service personnel has a certain time period to identify |
|||
* itself by inserting the right code via the keypad. Each key event is acknowledged via a short |
|||
* acoustic beep. The inserted code is checked after 4 digits have been entered. In case |
|||
* the correct code was inserted, a long beep, in case of a wrong code, three short |
|||
* beeps are issued. While the time period elapses, the "Alarm" LED flashes (the flashing accelerates |
|||
* every few seconds). When the correct code is inserted, the LED is continuously switched on. |
|||
* If the time expires without the right code being inserted, an alarm is raised via the AlarmManager. |
|||
*/ |
|||
class MaintenanceMode : public redBlocks::Core::NoCopyBase |
|||
{ |
|||
public: |
|||
/**
|
|||
* Constructor |
|||
*/ |
|||
MaintenanceMode(); |
|||
|
|||
/**
|
|||
* Enters the maintenance mode (when the door is opened) |
|||
*/ |
|||
void enter(); |
|||
|
|||
/**
|
|||
* Tries to leave the maintenance mode (leaving the maintenance mode is only allowed, |
|||
* when the right code was entered) |
|||
*/ |
|||
bool leave(); |
|||
|
|||
/**
|
|||
* This method must be called, when a button was pressed. It can be |
|||
* called from interrupt context, as it only schedules an event and returns immediately. |
|||
* @param[in] key the digit (0..9) that was inserted |
|||
*/ |
|||
void onKeyPressed( u8 key ) |
|||
{ |
|||
mKeyPressed = key; |
|||
Platform::OS::scheduleEvent( mKeyPressedEvent ); |
|||
} |
|||
|
|||
private: |
|||
/** Convenience definition */ |
|||
typedef MaintenanceMode ThisType; |
|||
|
|||
enum AlarmState |
|||
{ |
|||
ALARM_STATE_IDLE = 0, |
|||
ALARM_STATE_KEYCODE, |
|||
ALARM_STATE_ACCESS_GRANTED, |
|||
ALARM_STATE_ALARM |
|||
}; |
|||
|
|||
enum KeyCodeState |
|||
{ |
|||
KEY_CODE_STATE_IGNORE = 0, |
|||
KEY_CODE_STATE_INPUT, |
|||
KEY_CODE_STATE_CONFIRM_KEY_BEEP, |
|||
KEY_CODE_STATE_CONFIRM_CODE_BEEP, |
|||
KEY_CODE_STATE_ERROR_BEEP |
|||
}; |
|||
|
|||
/** Checks whether the inserted key code is correct */ |
|||
bool checkKeyCode() const; |
|||
|
|||
/** This method is called from mSoundTimer */ |
|||
static void onSoundTimerEvent( ThisType* t ); |
|||
|
|||
/** This method is called from mCountdownTimer */ |
|||
static void onCountdownTimerEvent( ThisType* t, u8 callCnt ); |
|||
|
|||
/** This method is called, when a key pressed event has been generated */ |
|||
static void onKeyPressedEvent( ThisType* t, u8 callCnt ); |
|||
|
|||
/** timer that is used to give feedback, when a button was pressed */ |
|||
Platform::OS::TIsrTimer<ThisType, &onSoundTimerEvent> mSoundTimer; |
|||
|
|||
/** timer that is used for the countdown after the door was opened */ |
|||
Platform::OS::TEventTimer<ThisType, &onCountdownTimerEvent> mCountdownTimer; |
|||
|
|||
/** event that is scheduled, when a button was pressed */ |
|||
Platform::OS::TEvent<ThisType, &onKeyPressedEvent> mKeyPressedEvent; |
|||
|
|||
/** the key that has been pressed */ |
|||
u8 mKeyPressed; |
|||
|
|||
/** the current alarm state */ |
|||
AlarmState mAlarmState; |
|||
|
|||
/** the counter used in certain alarm states */ |
|||
u8 mAlarmStateCounter; |
|||
|
|||
/** the current keycode state */ |
|||
KeyCodeState mKeyCodeState; |
|||
|
|||
/** the counter used in certain keycode states */ |
|||
u8 mKeyCodeStateCount; |
|||
|
|||
/** the keycode that has been input */ |
|||
u8 mKeyCode[4]; |
|||
|
|||
/** the helper class that is used to let the lamp flash */ |
|||
redBlocks::HAL::TDigitalOutputFlasher<Platform::KeyPadLamp, Platform::OS> mLampFlasher; |
|||
|
|||
}; |
|||
|
|||
#endif |
@ -0,0 +1 @@ |
|||
#include "ProductSlot.h" |
@ -0,0 +1,115 @@ |
|||
#ifndef PRODUCT_SLOT_H_ |
|||
#define PRODUCT_SLOT_H_ |
|||
|
|||
#include <Platform.h> |
|||
#include <Core/Base/IBase.h> |
|||
#include <Core/Base/NoCopyBase.h> |
|||
|
|||
/**
|
|||
* This class represents a single product slot, maintaining the price, the max number of |
|||
* items in the slot, the actual number of items in the slot and the slot's state. |
|||
*/ |
|||
class ProductSlot : public redBlocks::Core::NoCopyBase |
|||
{ |
|||
public: |
|||
/**
|
|||
* Constructor |
|||
*/ |
|||
ProductSlot() : mIsActive( false ) |
|||
{ |
|||
} |
|||
|
|||
/**
|
|||
* Configures a slot with the given values. |
|||
* @param numItems the number of total items that fit in the slot |
|||
* @param pricePerItem the price for the item |
|||
*/ |
|||
void configure( u8 numItems, u16 pricePerItem ) |
|||
{ |
|||
mNumItems = numItems; |
|||
mPricePerItem = pricePerItem; |
|||
} |
|||
|
|||
/**
|
|||
* Activates / deactivates the slot. Activating it, sets the number of |
|||
* items to the maximum number of items, i. e. this method must be called, |
|||
* when the slot is refilled. |
|||
* @param isActive true, if the slot is to be activated |
|||
*/ |
|||
void setActive( bool isActive ) |
|||
{ |
|||
mIsActive = isActive; |
|||
if ( isActive ) |
|||
{ |
|||
mItemCount = mNumItems; |
|||
} |
|||
} |
|||
|
|||
/**
|
|||
* This method must be called, if an item has been sold and is successfully released. |
|||
* @return the number of items left |
|||
*/ |
|||
u8 itemSold() |
|||
{ |
|||
u8 retval = 0; |
|||
if ( mIsActive ) |
|||
{ |
|||
if ( 0 < mItemCount ) |
|||
{ |
|||
--mItemCount; |
|||
} |
|||
retval = mItemCount; |
|||
} |
|||
return retval; |
|||
} |
|||
|
|||
/**
|
|||
* Returns the price of the item |
|||
* @return price per item in cent |
|||
*/ |
|||
u16 getPricePerItem() const |
|||
{ |
|||
return mPricePerItem; |
|||
} |
|||
|
|||
/**
|
|||
* Returns true, if the specified money entitles the customer to release the item |
|||
* (if the slot is empty or not active, this method returns false). |
|||
* @param money the money amount per 10 cent, i. e. value 15 means 150 cent |
|||
* @return true, if the item can be released |
|||
*/ |
|||
bool canRelease( u8 money ) const |
|||
{ |
|||
return ( mItemCount > 0 ) && ( money >= mPricePerItem ) && mIsActive; |
|||
} |
|||
|
|||
/**
|
|||
* Returns true, if the slot is active |
|||
* @return true, if the slot is active |
|||
*/ |
|||
bool getIsActive() const |
|||
{ |
|||
return mIsActive; |
|||
} |
|||
|
|||
/**
|
|||
* Returns the number of items left in the slot |
|||
* @return the number of items left in the slot |
|||
*/ |
|||
u8 getItemCount() const |
|||
{ |
|||
return mItemCount; |
|||
} |
|||
|
|||
private: |
|||
/** the number of total items that fit in the slot */ |
|||
u8 mNumItems; |
|||
/** the number of items available in the slot */ |
|||
u8 mItemCount; |
|||
/** the price per item in cent */ |
|||
u16 mPricePerItem; |
|||
/** true, if the slot is active */ |
|||
bool mIsActive; |
|||
}; |
|||
|
|||
#endif // PRODUCT_SLOT_H_
|
@ -0,0 +1,87 @@ |
|||
#ifndef T_TEMPERATURE_CONTROLLER_H_ |
|||
#define T_TEMPERATURE_CONTROLLER_H_ |
|||
|
|||
#include "AlarmManager.h" |
|||
|
|||
/**
|
|||
* This class works on an instance of T_TEMPERATURE_SENSOR and switches the |
|||
* cooling actor on, if the temperature rises above the specified level plus |
|||
* a hysteresis value. When it falls below the specified level minus the |
|||
* hysteresis level, it switches the cooling actor off. |
|||
* @tparam T_TEMPERATURE_SENSOR class that is used to retrieve the current |
|||
* temperature |
|||
* @tparam T_DIGITAL_OUTPUT the digital output driver that controls the |
|||
* cooling actor |
|||
*/ |
|||
template <class T_TEMPERATURE_SENSOR, class T_DIGITAL_OUTPUT> |
|||
class TTemperatureController |
|||
{ |
|||
public: |
|||
/**
|
|||
* Constructor |
|||
* @param[in] temperature the desired temperature |
|||
* @param[in] hysteresis the hysteresis to use when switching the |
|||
* cooling actor on and off |
|||
* @param[in] alarmTemperature if the temperature rises above this value, |
|||
* an alarm is issued via AlarmManager |
|||
*/ |
|||
TTemperatureController( s32 temperature, u32 hysteresis, s32 alarmTemperature ) : |
|||
mTemperatureOn( temperature + static_cast<s32>( hysteresis ) ), |
|||
mTemperatureOff( temperature - static_cast<s32>( hysteresis ) ), |
|||
mTemperatureAlarm( alarmTemperature ), |
|||
mIsCoolingOn( false ), |
|||
mIsOverheat( false ) |
|||
{ |
|||
} |
|||
|
|||
/**
|
|||
* This method must be called regularly (in the frequency, the |
|||
* temperature shall be controlled). It starts the temperature |
|||
* sampling. |
|||
*/ |
|||
void runOnce() |
|||
{ |
|||
mTemperatureSensor.sampleTemperature(); |
|||
} |
|||
|
|||
/**
|
|||
* This method must be called, when the sampling is done. |
|||
*/ |
|||
void onTemperatureAvailable() |
|||
{ |
|||
s32 temp = mTemperatureSensor.getLastSampledTemperature(); |
|||
if ( mIsCoolingOn ) |
|||
{ |
|||
if ( temp < mTemperatureOff ) |
|||
{ |
|||
mIsCoolingOn = false; |
|||
mIsOverheat = false; |
|||
T_DIGITAL_OUTPUT::setOutput( false ); |
|||
} |
|||
} |
|||
else |
|||
{ |
|||
if ( temp > mTemperatureOn ) |
|||
{ |
|||
mIsCoolingOn = true; |
|||
T_DIGITAL_OUTPUT::setOutput( true ); |
|||
} |
|||
} |
|||
if ( ( temp > mTemperatureAlarm ) && ( !mIsOverheat ) ) |
|||
{ |
|||
mIsOverheat = true; |
|||
AlarmManager::raiseAlarm( AlarmManager::ALARM_OVERHEAT ); |
|||
} |
|||
} |
|||
|
|||
private: |
|||
T_TEMPERATURE_SENSOR mTemperatureSensor; |
|||
s32 mTemperatureOn; |
|||
s32 mTemperatureOff; |
|||
s32 mTemperatureAlarm; |
|||
bool mIsCoolingOn; |
|||
bool mIsOverheat; |
|||
}; |
|||
|
|||
|
|||
#endif // T_TEMPERATURE_CONTROLLER_H_
|
@ -0,0 +1,235 @@ |
|||
#include "VendingMode.h" |
|||
#include "AlarmManager.h" |
|||
#include <Gui/VendingScreen.h> |
|||
|
|||
extern "C" void getChange( u16 moneyInBox, u16 itemPrice ); |
|||
|
|||
VendingMode::VendingMode() : |
|||
onFillupBtnPressed( &mInner ), |
|||
onReleaseMoneyBtnPressed( &mInner ) |
|||
{ |
|||
} |
|||
|
|||
void VendingMode::enter() |
|||
{ |
|||
mInner.mCashBox.setActivationState( true ); |
|||
mInner.mVendingState = Inner::STATE_WAITING; |
|||
VendingScreen::drawPrompt(); |
|||
} |
|||
|
|||
void VendingMode::leaveImmediate() |
|||
{ |
|||
mInner.mCashBox.setActivationState( false ); |
|||
if ( mInner.mVendingState == Inner::STATE_PRODUCT_SELECTED ) |
|||
{ |
|||
mInner.mSlotActors[mInner.mSelectedProduct].switchLamp( false ); |
|||
} |
|||
|
|||
mInner.mTimer.stop(); |
|||
mInner.mVendingState = Inner::STATE_INACTIVE; |
|||
for ( u8 i = 0; i < NUM_SLOTS; ++i ) |
|||
{ |
|||
mInner.mSlotActors[i].switchLamp( false ); |
|||
mInner.mSlotActors[i].switchFlap( false ); |
|||
} |
|||
Platform::DispenseBayLamp::setOutput( false ); |
|||
Platform::DisplayBacklight::setOutput( true ); |
|||
} |
|||
|
|||
|
|||
VendingMode::Inner::Inner() : |
|||
mTimer( this ), |
|||
mProductButtonPressedEvent( this ) |
|||
{ |
|||
mVendingState = STATE_INACTIVE; |
|||
mProductSlots[0].configure( 10, 240 ); |
|||
mProductSlots[1].configure( 10, 220 ); |
|||
mProductSlots[2].configure( 10, 180 ); |
|||
mProductSlots[3].configure( 10, 200 ); |
|||
|
|||
mSlotActors[0].switchLamp = Platform::Product1Lamp::setOutput; |
|||
mSlotActors[1].switchLamp = Platform::Product2Lamp::setOutput; |
|||
mSlotActors[2].switchLamp = Platform::Product3Lamp::setOutput; |
|||
mSlotActors[3].switchLamp = Platform::Product4Lamp::setOutput; |
|||
|
|||
mSlotActors[0].switchFlap = Platform::Product1ReleaseGear::setOutput; |
|||
mSlotActors[1].switchFlap = Platform::Product2ReleaseGear::setOutput; |
|||
mSlotActors[2].switchFlap = Platform::Product3ReleaseGear::setOutput; |
|||
mSlotActors[3].switchFlap = Platform::Product4ReleaseGear::setOutput; |
|||
|
|||
for ( u8 i = 0; i < NUM_SLOTS; ++i ) |
|||
{ |
|||
mProductSlots[i].setActive( true ); |
|||
} |
|||
|
|||
mCashBox.setActivationState( false ); |
|||
|
|||
Platform::CoinDetectorDriver::getInstanceRef().setCallback( *this ); |
|||
} |
|||
|
|||
void VendingMode::Inner::onCoinsInserted( u16 money ) |
|||
{ |
|||
mCashBox.onMoneyInserted( money ); |
|||
|
|||
bool isProductValid = |
|||
mVendingState == STATE_PRODUCT_SELECTED && |
|||
mProductSlots[mSelectedProduct].getIsActive() && |
|||
( 0 < mProductSlots[mSelectedProduct].getItemCount() ); |
|||
|
|||
if ( isProductValid || ( mVendingState == STATE_WAITING ) ) |
|||
{ |
|||
u16 price = 0; |
|||
if ( mVendingState == STATE_PRODUCT_SELECTED ) |
|||
{ |
|||
price = mProductSlots[mSelectedProduct].getPricePerItem(); |
|||
} |
|||
|
|||
if ( isProductValid && ( mProductSlots[mSelectedProduct].getPricePerItem() <= mCashBox.getMoneyInIntermediateCash() ) ) |
|||
{ |
|||
getChange(mCashBox.getMoneyInIntermediateCash(), mProductSlots[mSelectedProduct].getPricePerItem()); |
|||
startReleaseWorkflow(); |
|||
} |
|||
else |
|||
{ |
|||
VendingScreen::drawPriceInfo( price, mCashBox.getMoneyInIntermediateCash() ); |
|||
} |
|||
} |
|||
} |
|||
|
|||
void VendingMode::Inner::onFillupButtonPressedEvent( ThisType* t, u8 callCnt ) |
|||
{ |
|||
for ( u8 i = 0; i < NUM_SLOTS; ++i ) |
|||
{ |
|||
t->mProductSlots[i].setActive( true ); |
|||
} |
|||
} |
|||
|
|||
void VendingMode::Inner::onProductButtonPressedEvent( ThisType* t, u8 callCnt ) |
|||
{ |
|||
if ( ( t->mVendingState == STATE_WAITING ) || ( t->mVendingState == STATE_PRODUCT_SELECTED ) ) |
|||
{ |
|||
for ( u8 i = 0; i < NUM_SLOTS; ++i ) |
|||
{ |
|||
t->mSlotActors[i].switchLamp( false ); |
|||
} |
|||
|
|||
t->mVendingState = STATE_PRODUCT_SELECTED; |
|||
t->mSlotActors[t->mSelectedProduct].switchLamp( true ); |
|||
if ( ( !t->mProductSlots[t->mSelectedProduct].getIsActive() ) || ( 0 == t->mProductSlots[t->mSelectedProduct].getItemCount() ) ) |
|||
{ |
|||
VendingScreen::drawProductNotAvailableMessage(); |
|||
} |
|||
else |
|||
{ |
|||
if ( t->mProductSlots[t->mSelectedProduct].getPricePerItem() <= t->mCashBox.getMoneyInIntermediateCash() ) |
|||
{ |
|||
getChange(t->mCashBox.getMoneyInIntermediateCash(), t->mProductSlots[t->mSelectedProduct].getPricePerItem()); |
|||
t->startReleaseWorkflow(); |
|||
} |
|||
else |
|||
{ |
|||
VendingScreen::drawPriceInfo( t->mProductSlots[t->mSelectedProduct].getPricePerItem(), t->mCashBox.getMoneyInIntermediateCash() ); |
|||
} |
|||
} |
|||
} |
|||
} |
|||
|
|||
void VendingMode::Inner::onReleaseMoneyButtonPressedEvent( ThisType* t, u8 callCnt ) |
|||
{ |
|||
if ( ( t->mVendingState == STATE_WAITING ) || ( t->mVendingState == STATE_PRODUCT_SELECTED ) ) |
|||
{ |
|||
if ( t->mVendingState == STATE_PRODUCT_SELECTED ) |
|||
{ |
|||
t->mSlotActors[t->mSelectedProduct].switchLamp( false ); |
|||
} |
|||
t->mCashBox.releaseMoney(); |
|||
VendingScreen::drawReturningMoneyMessage(); |
|||
t->mVendingState = STATE_RETURN_MONEY; |
|||
t->mTimer.start( Platform::OS::Sec<3>::value ); |
|||
} |
|||
} |
|||
|
|||
void VendingMode::Inner::onTimerEvent( ThisType* t, u8 callCnt ) |
|||
{ |
|||
redBlocks::unused( callCnt ); |
|||
switch ( t->mVendingState ) |
|||
{ |
|||
case STATE_FLAP_OPEN: |
|||
t->mSlotActors[t->mSelectedProduct].switchFlap( false ); |
|||
if ( 2 == t->mReleaseLightBarrierEventCnt ) |
|||
{ |
|||
t->mCashBox.boxMoney(); |
|||
( void )t->mProductSlots[t->mSelectedProduct].itemSold(); |
|||
t->mVendingState = STATE_LAMP_ON; |
|||
t->mReleaseStateCounter = 0; |
|||
VendingScreen::drawTakeProductMessage(); |
|||
t->mTimer.start( Platform::OS::Sec<1>::value ); |
|||
} |
|||
else |
|||
{ |
|||
++t->mReleaseStateCounter; |
|||
if ( t->mReleaseStateCounter > 3 ) |
|||
{ |
|||
VendingScreen::drawProductErrorMessage(); |
|||
t->mCashBox.releaseMoney(); |
|||
t->mProductSlots[t->mSelectedProduct].setActive( false ); |
|||
AlarmManager::raiseAlarm( AlarmManager::ALARM_SLOT_BLOCKED ); |
|||
t->mVendingState = STATE_RETURN_MONEY; |
|||
t->mTimer.start( Platform::OS::Sec<3>::value ); |
|||
} |
|||
else |
|||
{ |
|||
t->mVendingState = STATE_FLAP_RETRY; |
|||
t->mTimer.start( Platform::OS::MilliSec<500>::value ); |
|||
} |
|||
} |
|||
break; |
|||
|
|||
case STATE_FLAP_RETRY: |
|||
t->mSlotActors[t->mSelectedProduct].switchFlap( true ); |
|||
t->mVendingState = STATE_FLAP_OPEN; |
|||
t->mTimer.start( Platform::OS::Sec<1>::value ); |
|||
break; |
|||
|
|||
case STATE_LAMP_ON: |
|||
Platform::DispenseBayLamp::setOutput( false ); |
|||
Platform::DisplayBacklight::setOutput( true ); |
|||
t->mVendingState = STATE_LAMP_OFF; |
|||
t->mTimer.start( Platform::OS::MilliSec<500>::value ); |
|||
break; |
|||
|
|||
case STATE_LAMP_OFF: |
|||
++t->mReleaseStateCounter; |
|||
if ( t->mReleaseStateCounter > 5 ) |
|||
{ |
|||
t->mVendingState = STATE_WAITING; |
|||
VendingScreen::drawPrompt(); |
|||
} |
|||
else |
|||
{ |
|||
Platform::DispenseBayLamp::setOutput( true ); |
|||
Platform::DisplayBacklight::setOutput( false ); |
|||
t->mVendingState = STATE_LAMP_ON; |
|||
t->mTimer.start( Platform::OS::MilliSec<500>::value ); |
|||
} |
|||
break; |
|||
case STATE_RETURN_MONEY: |
|||
t->mVendingState = STATE_WAITING; |
|||
VendingScreen::drawPrompt(); |
|||
case STATE_WAITING: |
|||
default: |
|||
// do nothing
|
|||
break; |
|||
} |
|||
} |
|||
|
|||
void VendingMode::Inner::startReleaseWorkflow() |
|||
{ |
|||
mSlotActors[mSelectedProduct].switchLamp( false ); |
|||
VendingScreen::drawReleaseMessage(); |
|||
mReleaseLightBarrierEventCnt = 0; |
|||
mVendingState = STATE_FLAP_OPEN; |
|||
mReleaseStateCounter = 0; |
|||
mSlotActors[mSelectedProduct].switchFlap( true ); |
|||
mTimer.start( Platform::OS::Sec<1>::value ); |
|||
} |
@ -0,0 +1,166 @@ |
|||
#ifndef VENDING_MODE_H_ |
|||
#define VENDING_MODE_H_ |
|||
|
|||
#include "CashBox.h" |
|||
#include "ProductSlot.h" |
|||
#include <Drivers/TCoinDetectorDriver.h> |
|||
|
|||
#include <Platform.h> |
|||
#include <Core/Base/IBase.h> |
|||
#include <Core/Base/NoCopyBase.h> |
|||
|
|||
/**
|
|||
* This class controls all product slots and the associated buttons |
|||
*/ |
|||
class VendingMode: public redBlocks::Core::NoCopyBase |
|||
{ |
|||
public: |
|||
/** the number of slots this product controller supports */ |
|||
static const u8 NUM_SLOTS = 4; |
|||
|
|||
private: |
|||
/**
|
|||
* This class implements the logic of class ProductController. The callback interface |
|||
* CashBox::IMoneyChangedCallback is implemented by this inner class, in order to keep |
|||
* the interface of the outer class clean. |
|||
*/ |
|||
class Inner : public Platform::CoinDetectorDriver::ICoinsInsertedCallback |
|||
{ |
|||
public: |
|||
/** More convenient definition of the own type. */ |
|||
typedef Inner ThisType; |
|||
/**
|
|||
* The states during the vending workflow |
|||
*/ |
|||
enum State |
|||
{ |
|||
STATE_INACTIVE = 0, |
|||
STATE_WAITING, |
|||
STATE_PRODUCT_SELECTED, |
|||
STATE_FLAP_OPEN, |
|||
STATE_FLAP_RETRY, |
|||
STATE_LAMP_ON, |
|||
STATE_LAMP_OFF, |
|||
STATE_RETURN_MONEY |
|||
}; |
|||
|
|||
/**
|
|||
* Constructor |
|||
*/ |
|||
Inner(); |
|||
|
|||
/**
|
|||
* This method is called by Platform::CoinDetectorDiriver when coins were inserted. |
|||
* @see ICoinsInsertedCallback |
|||
*/ |
|||
virtual void onCoinsInserted( u16 money ); |
|||
|
|||
/**
|
|||
* Starts the workflow to release the currently selected product |
|||
*/ |
|||
void startReleaseWorkflow(); |
|||
|
|||
/**
|
|||
* Structure that holds pointers to the methods that allow to switch the lamp |
|||
* and product release flap that correspond to a product slot |
|||
*/ |
|||
struct SlotActors |
|||
{ |
|||
void ( *switchLamp )( bool on ); |
|||
void ( *switchFlap )( bool open ); |
|||
}; |
|||
|
|||
/**
|
|||
* This event handler method is associated with mTimer. |
|||
*/ |
|||
static void onTimerEvent( ThisType*, u8 callCnt ); |
|||
|
|||
/**
|
|||
* This event handler method is associated with mFillupButtonPressedEvent |
|||
*/ |
|||
static void onFillupButtonPressedEvent( ThisType* t, u8 callCnt ); |
|||
|
|||
/**
|
|||
* This event handler method is associated with mProductButtonPressedEvent |
|||
*/ |
|||
static void onProductButtonPressedEvent( ThisType* t, u8 callCnt ); |
|||
|
|||
/**
|
|||
* This event handler method is associated with mReleaseMoneyButtonPressedEvent |
|||
*/ |
|||
static void onReleaseMoneyButtonPressedEvent( ThisType* t, u8 callCnt ); |
|||
|
|||
|
|||
/** used to invoke the method onTimerEvent after certain time periods */ |
|||
Platform::OS::TEventTimer<ThisType, &onTimerEvent> mTimer; |
|||
/** event that is scheduled, when a product button is pressed */ |
|||
Platform::OS::TEvent<ThisType, &onProductButtonPressedEvent> mProductButtonPressedEvent; |
|||
/** the instances representing a product slot */ |
|||
ProductSlot mProductSlots[NUM_SLOTS]; |
|||
/** array of function pointers via which the slot actors can be controlled */ |
|||
SlotActors mSlotActors[NUM_SLOTS]; |
|||
/** the cash box instance associated with this product controller */ |
|||
CashBox mCashBox; |
|||
/** the currently selected product */ |
|||
u8 mSelectedProduct; |
|||
/** the state the released item is in */ |
|||
State mVendingState; |
|||
/** the counter that is used within a state */ |
|||
u8 mReleaseStateCounter; |
|||
/** will be incremented, when the light barrier level changes during the release workflow */ |
|||
u8 mReleaseLightBarrierEventCnt; |
|||
}; |
|||
|
|||
Inner mInner; |
|||
|
|||
public: |
|||
/**
|
|||
* Constructor |
|||
*/ |
|||
VendingMode(); |
|||
|
|||
/**
|
|||
* Called when the vending mode is entered. |
|||
*/ |
|||
void enter(); |
|||
|
|||
/**
|
|||
* Called when the vending mode needs to be terminated (e. g. because |
|||
* the door was opened. It opens the cash box and does no longer react on |
|||
* button events. |
|||
*/ |
|||
void leaveImmediate(); |
|||
|
|||
/**
|
|||
* Called, when a product release button is pressed. It can be called from ISR |
|||
* context, as it does not perform any lenghty operations. |
|||
* @param btnIndex index of the button that was pressed |
|||
*/ |
|||
void onProductBtnPressed( u8 btnIndex ) |
|||
{ |
|||
mInner.mSelectedProduct = btnIndex; |
|||
Platform::OS::scheduleEvent( mInner.mProductButtonPressedEvent ); |
|||
} |
|||
|
|||
/**
|
|||
* Called when the light barrier input level changes. |
|||
*/ |
|||
void onLightBarrierEvent() |
|||
{ |
|||
++mInner.mReleaseLightBarrierEventCnt; |
|||
} |
|||
|
|||
/**
|
|||
* Functor that must be called, when the fillup buttion is pressed. It can be |
|||
* called from ISR context, as it only schedules an event and returns immediately. |
|||
*/ |
|||
Platform::OS::TEventFunc<Inner, &Inner::onFillupButtonPressedEvent> onFillupBtnPressed; |
|||
|
|||
/**
|
|||
* Functor that must be called, when the release money button was pressed. It can |
|||
* be called from ISR context, as it only schedules an event and returns immediately. |
|||
*/ |
|||
Platform::OS::TEventFunc<Inner, &Inner::onReleaseMoneyButtonPressedEvent> onReleaseMoneyBtnPressed; |
|||
}; |
|||
|
|||
#endif // VENDING_MODE_H_
|
@ -0,0 +1,123 @@ |
|||
#ifndef T_COIN_DETECTOR_DRIVER_H_ |
|||
#define T_COIN_DETECTOR_DRIVER_H_ |
|||
|
|||
#include <Core/Base/IBase.h> |
|||
#include <Core/Base/TGlobalPtrBase.h> |
|||
|
|||
/**
|
|||
* High level driver whose method @ref onCoinDetectorEvent() must be called from |
|||
* the receive ISR routine, when a byte is received from the communication interface |
|||
* via which the coin detector is connected |
|||
* @tparam T_COM_INTERFACE the communication interface class via which the coin detector |
|||
* messages are received |
|||
* @tparam T_EVENT_SCHEDULER the class that provides the methods to schedule |
|||
* mainloop events |
|||
*/ |
|||
template <class T_COM_INTERFACE, class T_EVENT_SCHEDULER> |
|||
class TCoinDetectorDriver : public redBlocks::Core::TGlobalPtrBase<TCoinDetectorDriver<T_COM_INTERFACE, T_EVENT_SCHEDULER> > |
|||
{ |
|||
private: |
|||
/** More convenient definition of the own type. */ |
|||
typedef TCoinDetectorDriver<T_COM_INTERFACE, T_EVENT_SCHEDULER> ThisType; |
|||
|
|||
public: |
|||
/**
|
|||
* An instance implementing this class must be associated with this driver instance |
|||
* and gets called, when one or more coins were inserted. |
|||
*/ |
|||
class ICoinsInsertedCallback : public redBlocks::Core::IBase |
|||
{ |
|||
public: |
|||
virtual void onCoinsInserted( u16 money ) = 0; |
|||
}; |
|||
|
|||
|
|||
/**
|
|||
* Constructor |
|||
*/ |
|||
TCoinDetectorDriver() : |
|||
mMoneyChangedEvent( this ), |
|||
mCallback( NULL ), |
|||
mMoney( 0 ) |
|||
{ |
|||
T_COM_INTERFACE::enableRecvDataCallback(); |
|||
} |
|||
|
|||
/**
|
|||
* Associates the callback with this driver. |
|||
* @param callback reference to the ICoinsInsertedCallback that is invoked from a |
|||
* synchronous event, after one ore more coins have been inserted |
|||
*/ |
|||
void setCallback( ICoinsInsertedCallback& callback ) |
|||
{ |
|||
mCallback = &callback; |
|||
} |
|||
|
|||
/**
|
|||
* This method must be called from the ISR callback, when a data byte is received |
|||
* from the coin detector. |
|||
*/ |
|||
void onCoinDetectorEvent() |
|||
{ |
|||
u16 amount = 0; |
|||
u8 coin; |
|||
// prevent another interrupt to interfere with this call
|
|||
T_COM_INTERFACE::disableRecvDataCallback(); |
|||
if ( 1 == T_COM_INTERFACE::getRecvData( &coin, 1 ) ) |
|||
{ |
|||
switch( coin ) |
|||
{ |
|||
case 0x30: |
|||
amount = 10; |
|||
break; |
|||
case 0x31: |
|||
amount = 20; |
|||
break; |
|||
case 0x32: |
|||
amount = 50; |
|||
break; |
|||
case 0x33: |
|||
amount = 100; |
|||
break; |
|||
case 0x34: |
|||
amount = 200; |
|||
break; |
|||
} |
|||
mMoney += amount; |
|||
} |
|||
T_COM_INTERFACE::enableRecvDataCallback(); |
|||
if ( amount != 0 ) |
|||
{ |
|||
mMoneyChangedEvent.schedule(); |
|||
} |
|||
} |
|||
|
|||
private: |
|||
/**
|
|||
* This method is associated with mMoneyChangedEvent in order to be called from the |
|||
* mainloop context after onCoinDetectorEvent() has been called from ISR context |
|||
*/ |
|||
static void onMoneyChangedEvent( ThisType* t, u8 callCnt ) |
|||
{ |
|||
T_COM_INTERFACE::disableRecvDataCallback(); |
|||
u16 money = t->mMoney; |
|||
t->mMoney = 0; |
|||
T_COM_INTERFACE::enableRecvDataCallback(); |
|||
|
|||
if ( NULL != t->mCallback ) |
|||
{ |
|||
t->mCallback->onCoinsInserted( money ); |
|||
} |
|||
} |
|||
|
|||
/** event instance that is scheduled from the ISR routine onCoinDetectorEvent() */ |
|||
typename T_EVENT_SCHEDULER::template TEvent<ThisType, &ThisType::onMoneyChangedEvent> mMoneyChangedEvent; |
|||
|
|||
/** the callback that wants to be informed, when the money has changed */ |
|||
ICoinsInsertedCallback* mCallback; |
|||
|
|||
/** the current money amount in cent */ |
|||
u16 mMoney; |
|||
}; |
|||
|
|||
#endif // T_COIN_DETECTOR_DRIVER_H_
|
@ -0,0 +1,53 @@ |
|||
#ifndef T_GSM_MODEM_DRIVER_H_ |
|||
#define T_GSM_MODEM_DRIVER_H_ |
|||
|
|||
#include <Core/Base/TGlobalPtrBase.h> |
|||
#include <HAL/TBufferedComInterfaceWriter.h> |
|||
|
|||
#include <string.h> |
|||
|
|||
/**
|
|||
* GSM modem driver that is capable of sending an SMS with AT commands. |
|||
* @tparam T_COM_INTERFACE the communication interface class via which to communicate |
|||
* with the modem |
|||
*/ |
|||
template <class T_COM_INTERFACE> |
|||
class TGsmModemDriver : public redBlocks::HAL::TBufferedComInterfaceWriter<T_COM_INTERFACE> |
|||
{ |
|||
public: |
|||
|
|||
typedef redBlocks::HAL::TBufferedComInterfaceWriter<T_COM_INTERFACE> BaseType; |
|||
|
|||
/**
|
|||
* Constructor |
|||
*/ |
|||
TGsmModemDriver() : BaseType( 220 ) |
|||
{ |
|||
} |
|||
|
|||
/**
|
|||
* Sends an SMS to the given number and with the given text |
|||
* @param number the zero terminated phone number like this +499217877730 |
|||
* @param message the zero terminated message to be sent |
|||
* @attention No length check is done within this method. The message must |
|||
* not be larger than 160 characters, the number must not exceed 20 characters |
|||
*/ |
|||
static void sendSms( const char* number, const char* message ) |
|||
{ |
|||
const char data1[] = "AT+CMGF=1\n"; |
|||
const char data2[] = "AT+CMGS=\""; |
|||
const char data3[] = "\"\n"; |
|||
const char data4 = 26; |
|||
const char data5[] = "\n"; |
|||
BaseType::write( data1, strlen( data1 ) )&& |
|||
BaseType::write( data2, strlen( data2 ) )&& |
|||
BaseType::write( number, strlen( number ) )&& |
|||
BaseType::write( data3, strlen( data3 ) )&& |
|||
BaseType::write( message, strlen( message ) )&& |
|||
BaseType::write( &data4, 1 )&& |
|||
BaseType::write( data5, strlen( data5 ) ); |
|||
|
|||
} |
|||
}; |
|||
|
|||
#endif // T_GSM_MODEM_DRIVER_H_
|
@ -0,0 +1,57 @@ |
|||
#ifndef T_TEMPERATURE_SENSOR_H_ |
|||
#define T_TEMPERATURE_SENSOR_H_ |
|||
|
|||
#include <HAL/TLinearInterpolator.h> |
|||
|
|||
/**
|
|||
* This class works on an analog input, and maps the values from there to a |
|||
* temperature value in the range from -10 to +40 degrees centigrade. |
|||
*/ |
|||
template <class T_ANALOG_INPUT> |
|||
class TTemperatureSensor |
|||
{ |
|||
public: |
|||
/** Constructor */ |
|||
TTemperatureSensor(); |
|||
/**
|
|||
* Returns the last sampled value in degrees * 1000, i. e. -5000 is returned for |
|||
* -5 degrees |
|||
* @return the last sampled value |
|||
*/ |
|||
s32 getLastSampledTemperature() |
|||
{ |
|||
// uses the interpolator to map the values according to the sensor curve
|
|||
return mInterpolator.interpolate( T_ANALOG_INPUT::getValue() ); |
|||
} |
|||
|
|||
void sampleTemperature() |
|||
{ |
|||
T_ANALOG_INPUT::sampleOnce(); |
|||
} |
|||
|
|||
private: |
|||
/** the interpolator type that is used */ |
|||
typedef redBlocks::HAL::TLinearInterpolator<u8, s32> InterpolatorType; |
|||
/** the curve data */ |
|||
static const InterpolatorType::Point mSensorCurve[]; |
|||
/** the interpolator instance */ |
|||
InterpolatorType mInterpolator; |
|||
}; |
|||
|
|||
// compile time initialization of the sensor curve
|
|||
template <class T_ANALOG_INPUT> |
|||
const typename TTemperatureSensor<T_ANALOG_INPUT>::InterpolatorType::Point |
|||
TTemperatureSensor<T_ANALOG_INPUT>::mSensorCurve[3] = |
|||
{ |
|||
{0x00, -10000}, |
|||
{0x80, +10000}, |
|||
{0xFF, +40000} |
|||
}; |
|||
|
|||
template <class T_ANALOG_INPUT> |
|||
TTemperatureSensor<T_ANALOG_INPUT>::TTemperatureSensor() |
|||
: mInterpolator( mSensorCurve, 3 ) |
|||
{ |
|||
} |
|||
|
|||
#endif // T_TEMPERATURE_SENSOR_H_
|
@ -0,0 +1,33 @@ |
|||
#ifndef GUI_H_ |
|||
#define GUI_H_ |
|||
|
|||
#include <Core/Base/TGlobalPtrBase.h> |
|||
#include <Platform.h> |
|||
#include <GUI/TGui.h> |
|||
#include "GuiData/Arial20.h" |
|||
#include "GuiData/Images.h" |
|||
|
|||
typedef redBlocks::GUI::TGui<Platform::Display> Gui; |
|||
|
|||
struct GuiResources : public redBlocks::Core::TGlobalPtrBase<GuiResources> |
|||
{ |
|||
GuiResources() : |
|||
fontArial20( GuiData::Arial20::data ), |
|||
bitmaskCoins( GuiData::Images::coins ) |
|||
{} |
|||
|
|||
Gui::Font fontArial20; |
|||
Gui::Bitmask bitmaskCoins; |
|||
}; |
|||
|
|||
struct GuiColorMap |
|||
{ |
|||
static const Gui::ColorValueType FOREGROUND = 1; |
|||
static const Gui::ColorValueType BACKGROUND = 0; |
|||
}; |
|||
|
|||
|
|||
|
|||
|
|||
|
|||
#endif // GUI_H_
|
@ -0,0 +1,330 @@ |
|||
|
|||
/*
|
|||
* This is a generated file, containing GUI data. Do not edit it manually! |
|||
*/ |
|||
#include <rbTypes.h> |
|||
|
|||
namespace GuiData |
|||
{ |
|||
namespace Arial20 |
|||
{ |
|||
extern const u8 data[]; |
|||
const u8 data[] = |
|||
{ |
|||
0x20, 0x7a, 0x14, 0x00, 0x1a, 0x00, 0x32, 0x00, |
|||
0x42, 0x00, 0x52, 0x00, 0x6f, 0x00, 0x89, 0x00, |
|||
0xb2, 0x00, 0x00, 0x00, 0xd1, 0x00, 0xe1, 0x00, |
|||
0xf4, 0x01, 0x07, 0x01, 0x24, 0x01, 0x32, 0x01, |
|||
0x42, 0x01, 0x50, 0x01, 0x63, 0x01, 0x7d, 0x01, |
|||
0x97, 0x01, 0xb1, 0x01, 0xcb, 0x01, 0xe5, 0x01, |
|||
0xff, 0x02, 0x19, 0x02, 0x33, 0x02, 0x4d, 0x02, |
|||
0x67, 0x02, 0x75, 0x02, 0x83, 0x02, 0xa0, 0x02, |
|||
0xbd, 0x02, 0xda, 0x02, 0xf4, 0x03, 0x22, 0x03, |
|||
0x44, 0x03, 0x63, 0x03, 0x85, 0x03, 0xa7, 0x03, |
|||
0xc6, 0x03, 0xe3, 0x04, 0x07, 0x04, 0x29, 0x04, |
|||
0x34, 0x04, 0x4c, 0x04, 0x6b, 0x04, 0x85, 0x04, |
|||
0xac, 0x04, 0xce, 0x04, 0xf2, 0x05, 0x11, 0x05, |
|||
0x35, 0x05, 0x57, 0x05, 0x76, 0x05, 0x95, 0x05, |
|||
0xb7, 0x05, 0xd9, 0x06, 0x05, 0x06, 0x22, 0x06, |
|||
0x41, 0x06, 0x5e, 0x06, 0x6c, 0x06, 0x7f, 0x00, |
|||
0x00, 0x06, 0x8d, 0x00, 0x00, 0x06, 0xa7, 0x06, |
|||
0xc1, 0x06, 0xdb, 0x06, 0xf3, 0x07, 0x0d, 0x07, |
|||
0x27, 0x07, 0x37, 0x07, 0x51, 0x07, 0x6b, 0x07, |
|||
0x76, 0x07, 0x84, 0x07, 0x9c, 0x07, 0xa7, 0x07, |
|||
0xcb, 0x07, 0xe5, 0x07, 0xff, 0x08, 0x19, 0x08, |
|||
0x33, 0x08, 0x43, 0x08, 0x5b, 0x08, 0x69, 0x08, |
|||
0x83, 0x08, 0xa0, 0x08, 0xc7, 0x08, 0xdf, 0x08, |
|||
0xfc, 0x0a, 0xff, 0x07, 0x18, 0x60, 0x9e, 0xfd, |
|||
0x3e, 0x7f, 0x78, 0xe0, 0xc1, 0x86, 0x19, 0x63, |
|||
0x86, 0x19, 0x06, 0x98, 0x61, 0x86, 0x01, 0x06, |
|||
0x18, 0xe0, 0xff, 0x09, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x30, 0x0c, |
|||
0xc3, 0x30, 0x0c, 0xc3, 0x30, 0x0c, 0xc0, 0x30, |
|||
0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0xd8, 0xb6, |
|||
0x6d, 0xdb, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x0b, 0x00, 0x00, 0x00, 0x00, |
|||
0x60, 0x06, 0x33, 0xcc, 0xfc, 0xff, 0xff, 0x98, |
|||
0xe1, 0x0e, 0x33, 0xfe, 0xff, 0x7f, 0x66, 0x98, |
|||
0xc1, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x0a, 0x00, 0x00, 0x00, 0x02, 0x3e, 0xfc, 0x99, |
|||
0x6c, 0x82, 0x0b, 0x7c, 0xc0, 0x07, 0x3e, 0xc8, |
|||
0x26, 0xbb, 0xce, 0x1f, 0x3e, 0x20, 0x80, 0x00, |
|||
0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x3c, 0x0c, 0x66, 0x06, 0x66, 0x06, 0x66, |
|||
0x03, 0x66, 0x03, 0xe6, 0x03, 0xbc, 0x3d, 0x80, |
|||
0x67, 0xc0, 0x66, 0xc0, 0x66, 0x60, 0x66, 0x60, |
|||
0x66, 0x30, 0x3c, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x0f, 0xf8, 0x81, 0x19, 0x98, 0x81, 0x0d, |
|||
0x70, 0xc0, 0x07, 0x6c, 0x66, 0x6c, 0x86, 0xe3, |
|||
0x38, 0xfc, 0x87, 0xc7, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x06, 0x00, 0x00, 0x80, 0x10, 0xc2, |
|||
0x30, 0x86, 0x61, 0x18, 0x86, 0x61, 0x30, 0x0c, |
|||
0x02, 0x81, 0x07, 0x00, 0x00, 0x00, 0xe1, 0x43, |
|||
0x50, 0x28, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, |
|||
0x00, 0xe1, 0x43, 0x50, 0x28, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x0b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x30, 0x80, 0x01, 0x0c, 0x60, 0xf0, 0xbf, 0xff, |
|||
0xc1, 0x00, 0x06, 0x30, 0x80, 0x01, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x63, |
|||
0x88, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0xf0, 0x7d, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x63, 0x00, 0x00, |
|||
0x00, 0x07, 0x00, 0x00, 0x00, 0x06, 0xc3, 0x60, |
|||
0x30, 0x0c, 0x06, 0xc3, 0x60, 0x30, 0x0c, 0x06, |
|||
0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, |
|||
0x00, 0x1e, 0xfc, 0x38, 0x67, 0x98, 0x61, 0x86, |
|||
0x19, 0x66, 0x98, 0x61, 0x86, 0x39, 0xc7, 0x0f, |
|||
0x1e, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, |
|||
0x00, 0x00, 0x00, 0x18, 0x70, 0xe0, 0xc1, 0x06, |
|||
0x19, 0x60, 0x80, 0x01, 0x06, 0x18, 0x60, 0x80, |
|||
0x01, 0x06, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x0a, 0x00, 0x00, 0x00, 0x00, 0x1e, 0xfc, 0x38, |
|||
0x67, 0x18, 0x60, 0x80, 0x01, 0x03, 0x06, 0x0c, |
|||
0x1c, 0x30, 0xe0, 0x9f, 0x7f, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x0e, |
|||
0x7c, 0x18, 0x03, 0x0c, 0x30, 0x70, 0xc0, 0x03, |
|||
0x18, 0x60, 0x86, 0x19, 0xc6, 0x0f, 0x1e, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, |
|||
0x00, 0x18, 0x70, 0xc0, 0x81, 0x07, 0x1b, 0x6c, |
|||
0x98, 0x31, 0xc6, 0x7f, 0xff, 0x81, 0x01, 0x06, |
|||
0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, |
|||
0x00, 0x00, 0x00, 0x3f, 0xfc, 0x30, 0x60, 0x80, |
|||
0x1d, 0xfe, 0x18, 0x06, 0x18, 0x60, 0x86, 0x19, |
|||
0xc6, 0x0f, 0x1e, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x0a, 0x00, 0x00, 0x00, 0x00, 0x1e, 0xfc, 0x30, |
|||
0x66, 0x80, 0x01, 0x76, 0xf8, 0xe3, 0x98, 0x61, |
|||
0x86, 0x31, 0xc6, 0x0f, 0x1e, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x80, 0x7f, |
|||
0xfe, 0x01, 0x02, 0x0c, 0x18, 0x60, 0xc0, 0x00, |
|||
0x03, 0x0c, 0x38, 0x60, 0x80, 0x01, 0x06, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, |
|||
0x00, 0x1e, 0xfc, 0x18, 0x66, 0x98, 0x61, 0xfc, |
|||
0xf0, 0x63, 0x98, 0x61, 0x86, 0x19, 0xc6, 0x0f, |
|||
0x1e, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, |
|||
0x00, 0x00, 0x00, 0x1e, 0xfc, 0x18, 0x66, 0x98, |
|||
0x61, 0xc6, 0xf1, 0x87, 0x1b, 0x60, 0x80, 0x19, |
|||
0xc3, 0x0f, 0x1e, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x05, 0x00, 0x00, 0x00, 0x00, 0x63, 0x00, 0x00, |
|||
0x00, 0x00, 0x63, 0x00, 0x00, 0x00, 0x05, 0x00, |
|||
0x00, 0x00, 0x00, 0x63, 0x00, 0x00, 0x00, 0x00, |
|||
0x63, 0x88, 0x00, 0x00, 0x0b, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x0e, 0x3e, |
|||
0x3c, 0x30, 0x00, 0x0f, 0xe0, 0x03, 0x38, 0x00, |
|||
0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x0b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0xf8, 0xcf, 0x7f, 0x00, 0x00, 0x80, |
|||
0xff, 0xfc, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0b, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x38, |
|||
0x80, 0x0f, 0xe0, 0x01, 0x18, 0x78, 0xf8, 0xe0, |
|||
0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, |
|||
0x1e, 0xfc, 0x38, 0x67, 0x18, 0x60, 0xc0, 0x80, |
|||
0x01, 0x03, 0x06, 0x18, 0x00, 0x80, 0x01, 0x06, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x12, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0xe0, 0x07, 0xe0, |
|||
0x7f, 0xc0, 0x81, 0x83, 0x71, 0x1f, 0xe3, 0xef, |
|||
0xcc, 0x1c, 0x9b, 0x63, 0x6c, 0x86, 0xb1, 0x19, |
|||
0xc2, 0x66, 0x8c, 0x99, 0x33, 0x67, 0xfc, 0x0f, |
|||
0x73, 0x0f, 0x1c, 0x80, 0xe3, 0x01, 0x07, 0xff, |
|||
0x0f, 0xf0, 0x0f, 0x0d, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x70, 0x00, 0x0e, 0x60, 0x03, 0x6c, 0x80, |
|||
0x0d, 0x18, 0x03, 0x63, 0xe0, 0x0f, 0xfe, 0xc3, |
|||
0x60, 0x18, 0x8c, 0x01, 0x33, 0x60, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, |
|||
0x00, 0x00, 0xe0, 0x1f, 0xfe, 0x63, 0x60, 0x06, |
|||
0x66, 0x60, 0xfe, 0xe3, 0x3f, 0x06, 0x66, 0x60, |
|||
0x06, 0x66, 0x70, 0xfe, 0xe3, 0x1f, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x0d, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0xf8, 0x80, 0x7f, 0x38, 0x1c, 0x03, |
|||
0x33, 0x00, 0x06, 0xc0, 0x00, 0x18, 0x00, 0x03, |
|||
0xc0, 0xc0, 0x38, 0x0c, 0xfe, 0x01, 0x0f, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0d, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0xff, 0xe0, 0x3f, 0x0c, |
|||
0x8e, 0x81, 0x33, 0x60, 0x06, 0xcc, 0x80, 0x19, |
|||
0x30, 0x03, 0x66, 0x60, 0x0c, 0x8e, 0xff, 0xf0, |
|||
0x0f, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x0c, 0x00, 0x00, 0x00, 0x00, 0xe0, 0x7f, 0xfe, |
|||
0x67, 0x00, 0x06, 0x60, 0x00, 0xfe, 0xe3, 0x3f, |
|||
0x06, 0x60, 0x00, 0x06, 0x60, 0x00, 0xfe, 0xe7, |
|||
0x7f, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0b, |
|||
0x00, 0x00, 0x00, 0x00, 0xfc, 0xe7, 0x3f, 0x03, |
|||
0x18, 0xc0, 0x00, 0xfe, 0xf1, 0x8f, 0x01, 0x0c, |
|||
0x60, 0x00, 0x03, 0x18, 0xc0, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x0e, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x80, 0x0f, 0xf8, 0x0f, 0x07, 0xc3, |
|||
0x80, 0x19, 0x00, 0x06, 0x80, 0xe1, 0x67, 0xf8, |
|||
0x19, 0x60, 0x0c, 0x18, 0x07, 0x87, 0xff, 0x80, |
|||
0x0f, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x0d, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x66, |
|||
0xc0, 0x0c, 0x98, 0x01, 0x33, 0x60, 0xfe, 0xcf, |
|||
0xff, 0x19, 0x30, 0x03, 0x66, 0xc0, 0x0c, 0x98, |
|||
0x01, 0x33, 0x60, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x04, 0x00, 0x60, 0x66, 0x66, 0x66, |
|||
0x66, 0x66, 0x66, 0x00, 0x00, 0x09, 0x00, 0x00, |
|||
0x00, 0x00, 0x06, 0x0c, 0x18, 0x30, 0x60, 0xc0, |
|||
0x80, 0x01, 0x03, 0x66, 0xcc, 0x98, 0x1f, 0x1e, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, |
|||
0x00, 0x00, 0x60, 0x70, 0x86, 0x63, 0x1c, 0xe6, |
|||
0x60, 0x07, 0x3e, 0xe0, 0x07, 0xee, 0x60, 0x1c, |
|||
0x86, 0x61, 0x38, 0x06, 0x67, 0xe0, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, |
|||
0x80, 0x01, 0x06, 0x18, 0x60, 0x80, 0x01, 0x06, |
|||
0x18, 0x60, 0x80, 0x01, 0x06, 0x18, 0xe0, 0x9f, |
|||
0x7f, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0xc0, 0x01, 0xe7, 0xc1, |
|||
0xf3, 0xe0, 0x79, 0xf0, 0x6c, 0x6c, 0x36, 0x36, |
|||
0x1b, 0x9b, 0x89, 0xcc, 0x6c, 0x66, 0x36, 0x33, |
|||
0x9b, 0x19, 0xc7, 0x8c, 0x63, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x0d, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x03, 0xe6, 0xc0, 0x3c, 0x98, |
|||
0x07, 0xb3, 0x61, 0x66, 0xcc, 0x9c, 0x19, 0x33, |
|||
0xc3, 0x66, 0xf0, 0x0c, 0x9e, 0x81, 0x33, 0x60, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0e, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x80, 0x0f, 0xf8, |
|||
0x07, 0x87, 0xc3, 0xc0, 0x18, 0x60, 0x06, 0x98, |
|||
0x01, 0x66, 0x80, 0x19, 0x60, 0x0c, 0x0c, 0x87, |
|||
0x83, 0x7f, 0x80, 0x07, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, |
|||
0xe0, 0x1f, 0xfe, 0x63, 0x70, 0x06, 0x66, 0x60, |
|||
0x06, 0xe7, 0x3f, 0xfe, 0x61, 0x00, 0x06, 0x60, |
|||
0x00, 0x06, 0x60, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x0e, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0xc0, 0x0f, 0xf8, 0x07, 0x87, 0xc3, 0xc0, 0x19, |
|||
0x60, 0x06, 0x98, 0x01, 0x66, 0x80, 0x19, 0x60, |
|||
0x8c, 0x0d, 0xc7, 0x81, 0x7f, 0xc0, 0x77, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0d, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0xff, 0xe1, 0x7f, 0x0c, |
|||
0x9c, 0x01, 0x33, 0x70, 0xfe, 0xc7, 0x7f, 0x18, |
|||
0x06, 0xc3, 0x61, 0x70, 0x0c, 0x8c, 0x81, 0x33, |
|||
0xe0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1f, 0xfc, |
|||
0xe3, 0x70, 0x06, 0x66, 0x00, 0x3c, 0x80, 0x1f, |
|||
0xc0, 0x03, 0x60, 0x06, 0xe6, 0x70, 0xfc, 0x83, |
|||
0x1f, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0c, |
|||
0x00, 0x00, 0x00, 0x00, 0xe0, 0x7f, 0xfe, 0x07, |
|||
0x06, 0x60, 0x00, 0x06, 0x60, 0x00, 0x06, 0x60, |
|||
0x00, 0x06, 0x60, 0x00, 0x06, 0x60, 0x00, 0x06, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0d, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x03, 0x66, 0xc0, 0x0c, |
|||
0x98, 0x01, 0x33, 0x60, 0x06, 0xcc, 0x80, 0x19, |
|||
0x30, 0x03, 0x66, 0xc0, 0x1c, 0x0c, 0xff, 0x81, |
|||
0x0f, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x0d, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x66, |
|||
0xc0, 0x18, 0x0c, 0x83, 0x61, 0x30, 0x18, 0x03, |
|||
0x63, 0x60, 0x0c, 0xd8, 0x00, 0x1b, 0x60, 0x03, |
|||
0x38, 0x00, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x11, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x18, 0x1c, 0x3c, 0x38, 0xd8, 0xd8, 0x98, |
|||
0xb1, 0x31, 0x63, 0x63, 0xc6, 0xc6, 0x8c, 0x88, |
|||
0xb1, 0xb1, 0x61, 0x63, 0xc3, 0xc6, 0x86, 0x8d, |
|||
0x0d, 0x0e, 0x0e, 0x1c, 0x1c, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0b, 0x00, |
|||
0x00, 0x00, 0x00, 0x1c, 0xc7, 0x18, 0x6c, 0x60, |
|||
0x03, 0x0e, 0x70, 0x80, 0x03, 0x36, 0xb0, 0xc1, |
|||
0x1d, 0xc6, 0x18, 0xec, 0xe0, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, |
|||
0x70, 0xe0, 0x06, 0xc6, 0x30, 0x9c, 0x83, 0x19, |
|||
0xf0, 0x00, 0x0f, 0x60, 0x00, 0x06, 0x60, 0x00, |
|||
0x06, 0x60, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x0b, 0x00, 0x00, 0x00, 0x00, 0xfc, |
|||
0xe7, 0x3f, 0xc0, 0x00, 0x03, 0x1c, 0x60, 0x80, |
|||
0x01, 0x06, 0x38, 0xc0, 0x00, 0x03, 0xfc, 0xef, |
|||
0x7f, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x05, |
|||
0x00, 0x00, 0xef, 0x8d, 0x31, 0xc6, 0x18, 0x63, |
|||
0x8c, 0x31, 0xc6, 0x78, 0xf0, 0x07, 0x00, 0x00, |
|||
0xc0, 0x60, 0x60, 0x30, 0x18, 0x18, 0x0c, 0x06, |
|||
0x06, 0x83, 0x81, 0xc1, 0x00, 0x00, 0x00, 0x00, |
|||
0x05, 0x00, 0x80, 0xf7, 0x18, 0x63, 0x8c, 0x31, |
|||
0xc6, 0x18, 0x63, 0x8c, 0xbd, 0x70, 0x0a, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0xf0, 0xff, 0xff, |
|||
0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x80, 0x0f, 0x7f, 0x86, 0x81, 0xc7, 0x9f, 0x67, |
|||
0x86, 0x19, 0xe7, 0x1f, 0x6f, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x80, 0x01, |
|||
0x06, 0x18, 0x60, 0x87, 0x3f, 0xce, 0x19, 0x66, |
|||
0x98, 0x61, 0x86, 0x39, 0xe7, 0x8f, 0x1d, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x1e, 0x7e, 0xce, 0x0c, |
|||
0x18, 0x30, 0x60, 0xc0, 0x19, 0x3f, 0x3c, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, |
|||
0x00, 0x60, 0x80, 0x01, 0x86, 0x1b, 0x7f, 0xce, |
|||
0x19, 0x66, 0x98, 0x61, 0x86, 0x39, 0xc7, 0x1f, |
|||
0x6e, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80, 0x07, |
|||
0x3f, 0xce, 0x18, 0xe6, 0x9f, 0x7f, 0x06, 0x38, |
|||
0xc6, 0x0f, 0x1e, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x06, 0x00, 0x00, 0xf0, 0xbe, 0xf1, 0x7d, 0x86, |
|||
0x61, 0x18, 0x86, 0x61, 0x18, 0x00, 0x00, 0x00, |
|||
0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x80, 0x1b, 0x7f, 0xce, 0x19, 0x66, 0x98, 0x61, |
|||
0x86, 0x39, 0xc7, 0x1f, 0x6e, 0x80, 0x19, 0xe7, |
|||
0x0f, 0x1f, 0x0a, 0x00, 0x00, 0x00, 0x80, 0x01, |
|||
0x06, 0x18, 0x60, 0x8f, 0x7f, 0x8e, 0x19, 0x66, |
|||
0x98, 0x61, 0x86, 0x19, 0x66, 0x98, 0x61, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x60, 0x06, |
|||
0x66, 0x66, 0x66, 0x66, 0x66, 0x00, 0x00, 0x05, |
|||
0x00, 0x00, 0xc6, 0x00, 0x63, 0x8c, 0x31, 0xc6, |
|||
0x18, 0x63, 0x8c, 0xbd, 0x30, 0x09, 0x00, 0x00, |
|||
0x00, 0x30, 0x60, 0xc0, 0x80, 0x71, 0x73, 0x76, |
|||
0x3c, 0xf8, 0xb0, 0x61, 0xc6, 0x8c, 0x31, 0xe3, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x60, |
|||
0x66, 0x66, 0x66, 0x66, 0x66, 0x66, 0x00, 0x00, |
|||
0x0e, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x60, 0xe7, 0xf8, 0x7d, 0xce, |
|||
0x99, 0x31, 0x66, 0x8c, 0x19, 0x63, 0xc6, 0x98, |
|||
0x31, 0x66, 0x8c, 0x19, 0x63, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x60, 0x8f, 0x7f, 0x8e, |
|||
0x19, 0x66, 0x98, 0x61, 0x86, 0x19, 0x66, 0x98, |
|||
0x61, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80, 0x07, |
|||
0x3f, 0xce, 0x19, 0x66, 0x98, 0x61, 0x86, 0x39, |
|||
0xc7, 0x0f, 0x1e, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x60, 0x87, 0x3f, 0xce, 0x19, 0x66, 0x98, 0x61, |
|||
0x86, 0x39, 0xe7, 0x8f, 0x1d, 0x06, 0x18, 0x60, |
|||
0x80, 0x01, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x80, 0x1b, 0x7f, 0xce, 0x19, 0x66, |
|||
0x98, 0x61, 0x86, 0x39, 0xc7, 0x1f, 0x6e, 0x80, |
|||
0x01, 0x06, 0x18, 0x60, 0x06, 0x00, 0x00, 0x00, |
|||
0x00, 0x60, 0xfb, 0x8e, 0x61, 0x18, 0x86, 0x61, |
|||
0x18, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x1f, 0x7f, 0xc6, 0x1c, |
|||
0xf0, 0x80, 0x03, 0xce, 0x98, 0x3f, 0x3e, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x63, |
|||
0xcc, 0x7b, 0xc6, 0x18, 0x63, 0x8c, 0x73, 0x00, |
|||
0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x60, 0x98, 0x61, 0x86, 0x19, 0x66, |
|||
0x98, 0x61, 0x86, 0x19, 0xe7, 0x1f, 0x6f, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x0b, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0xcc, 0x60, |
|||
0x8c, 0x61, 0x0c, 0x63, 0xb0, 0x81, 0x0d, 0x38, |
|||
0xc0, 0x01, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x0f, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0xc2, 0x8c, |
|||
0x63, 0xc6, 0x31, 0xa6, 0x0c, 0xdb, 0x86, 0x6d, |
|||
0x83, 0xa2, 0xc0, 0x71, 0xe0, 0x38, 0x60, 0x0c, |
|||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xc0, |
|||
0x30, 0x33, 0x66, 0x78, 0x60, 0xc0, 0xc0, 0xc3, |
|||
0x8c, 0x99, 0x61, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x0b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
|||
0x00, 0x18, 0xcc, 0x60, 0x8c, 0x61, 0x0c, 0x66, |
|||
0xb0, 0x01, 0x0f, 0x78, 0x80, 0x01, 0x0c, 0x60, |
|||
0x80, 0x01, 0x0f, 0x38, 0x00, 0x08, 0x00, 0x00, |
|||
0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xe0, 0x70, |
|||
0x38, 0x1c, 0x0e, 0x07, 0xff, 0xff, 0x00, 0x00, |
|||
0x00, 0x00 |
|||
}; |
|||
} |
|||
} |
@ -0,0 +1,13 @@ |
|||
|
|||
/*
|
|||
* This is a generated file, containing GUI data. Do not edit it manually! |
|||
*/ |
|||
#include <rbTypes.h> |
|||
|
|||
namespace GuiData |
|||
{ |
|||
namespace Arial20 |
|||
{ |
|||
extern const u8 data[]; |
|||
} |
|||
} |
@ -0,0 +1,32 @@ |
|||
|
|||
/*
|
|||
* This is a generated file, containing GUI data. Do not edit it manually! |
|||
*/ |
|||
#include <rbTypes.h> |
|||
|
|||
namespace GuiData |
|||
{ |
|||
namespace Images |
|||
{ |
|||
extern const u8 coins[]; |
|||
const u8 coins[] = |
|||
{ |
|||
33, 29, /* width and height */ |
|||
0x00, 0x00, 0xfe, 0x00, 0x00, 0x00, 0xff, 0x07, |
|||
0x00, 0x80, 0x07, 0x3c, 0x00, 0x80, 0x03, 0xe0, |
|||
0x00, 0xa0, 0x03, 0x80, 0x03, 0xa0, 0x03, 0x1f, |
|||
0x0e, 0x28, 0x03, 0x7f, 0x18, 0x68, 0x03, 0x87, |
|||
0x60, 0xc8, 0x06, 0x03, 0xc0, 0xd8, 0x06, 0x06, |
|||
0x00, 0xb3, 0x0d, 0x06, 0x00, 0xb6, 0x19, 0xfe, |
|||
0x07, 0x6c, 0x33, 0x18, 0x00, 0x78, 0x66, 0xf8, |
|||
0x0f, 0xf0, 0xcc, 0x60, 0x00, 0xe0, 0x99, 0x81, |
|||
0x01, 0xc0, 0x33, 0x06, 0x03, 0xc0, 0x66, 0x0c, |
|||
0x1c, 0x82, 0x8d, 0x31, 0xf0, 0x87, 0x19, 0xe3, |
|||
0xc0, 0x87, 0x63, 0x8c, 0x03, 0x80, 0xc3, 0x38, |
|||
0x0e, 0x80, 0x03, 0xe3, 0x78, 0xc0, 0x03, 0x8e, |
|||
0xc3, 0xff, 0x01, 0x38, 0x1e, 0xfe, 0x00, 0xe0, |
|||
0xf0, 0x63, 0x00, 0x80, 0x87, 0x3f, 0x00, 0x00, |
|||
0xfc, 0x18, 0x00, 0x00, 0xe0, 0x0f, 0x00, 0x00 |
|||
}; |
|||
} |
|||
} |
@ -0,0 +1,13 @@ |
|||
|
|||
/*
|
|||
* This is a generated file, containing GUI data. Do not edit it manually! |
|||
*/ |
|||
#include <rbTypes.h> |
|||
|
|||
namespace GuiData |
|||
{ |
|||
namespace Images |
|||
{ |
|||
extern const u8 coins[]; |
|||
} |
|||
} |
@ -0,0 +1,17 @@ |
|||
P1 |
|||
# CREATOR: GIMP PNM Filter Version 1.1 |
|||
33 29 |
|||
0000000000000000011111110000000000000000000000001111111111100000000000 |
|||
0000000001111000000011110000000000000000011100000000000111000000000000 |
|||
0101110000000000000111000000000001011100000011111000011100000001010011 |
|||
0000001111111000011000000101101100000011100001000001100001001101100000 |
|||
1100000000000011000110110110000001100000000000001100110110110000011000 |
|||
0000000000011011011001100001111111111000000011011011001100000110000000 |
|||
0000000111100110011000011111111100000000111100110011000001100000000000 |
|||
0001111001100110000001100000000000001111001100011000001100000000000011 |
|||
0110011000110000001110000100000110110001100011000000111111100001100110 |
|||
0011000111000000111110000111000110001100011100000000000001110000110001 |
|||
1100011100000000000111000000110001110001111000000011110000000111000111 |
|||
0000111111111110000000000111000111100001111111000000000000011100001111 |
|||
1100011000000000000000011110000111111100000000000000000000111111000110 |
|||
00000000000000000000000111111100000000000000000 |
@ -0,0 +1,41 @@ |
|||
#include <Core/Error/Error.h> |
|||
#include "MaintenanceScreen.h" |
|||
#include "Gui.h" |
|||
|
|||
|
|||
static void drawTwoLineMessage( const char* line1, const char* line2 ) |
|||
{ |
|||
Gui::clear( GuiColorMap::BACKGROUND ); |
|||
Gui::paint( GuiResources::getInstanceRef().fontArial20.text( line1 ), Gui::CenterHorizontal(), Gui::BottomAlign( Gui::Display::getHeight() / 2 ), GuiColorMap::FOREGROUND ); |
|||
Gui::paint( GuiResources::getInstanceRef().fontArial20.text( line2 ), Gui::CenterHorizontal(), Gui::TopAlign( Gui::Display::getHeight() / 2 ), GuiColorMap::FOREGROUND ); |
|||
Gui::update(); |
|||
} |
|||
|
|||
|
|||
void MaintenanceScreen::drawAlarmCodePromptMessage( u8 numDigits ) |
|||
{ |
|||
RB_FATAL_ASSERT( numDigits <= 4 ); |
|||
const char codeStr[] = "####"; |
|||
char code[sizeof( codeStr )]; |
|||
::memcpy( code, codeStr, sizeof( codeStr ) ); |
|||
|
|||
Gui::CoordinateType width = GuiResources::getInstanceRef().fontArial20.text( code ).getWidth(); |
|||
Gui::CoordinateType x = 0; |
|||
if ( width < Gui::Display::getWidth() ) |
|||
{ |
|||
x = ( Gui::Display::getWidth() - width ) / 2; |
|||
} |
|||
Gui::clear( GuiColorMap::BACKGROUND ); |
|||
Gui::paint( GuiResources::getInstanceRef().fontArial20.text( "Enter code!" ), Gui::CenterHorizontal(), Gui::BottomAlign( Gui::Display::getHeight() / 2 ), GuiColorMap::FOREGROUND ); |
|||
if ( 0 != numDigits ) |
|||
{ |
|||
code[numDigits] = 0; |
|||
Gui::paint( GuiResources::getInstanceRef().fontArial20.text( code ), Gui::LeftAlign( x ), Gui::TopAlign( Gui::Display::getHeight() / 2 ), GuiColorMap::FOREGROUND ); |
|||
} |
|||
Gui::update(); |
|||
} |
|||
|
|||
void MaintenanceScreen::drawMaintenanceModeMessage() |
|||
{ |
|||
drawTwoLineMessage( "Maintenance", "Mode" ); |
|||
} |
@ -0,0 +1,17 @@ |
|||
#ifndef MAINTENANCE_SCREEN_H_ |
|||
#define MAINTENANCE_SCREEN_H_ |
|||
|
|||
#include <Core/Base/NoInstanceBase.h> |
|||
|
|||
/**
|
|||
* This class paints maintenance messages to the screen. |
|||
*/ |
|||
class MaintenanceScreen : public redBlocks::Core::NoInstanceBase |
|||
{ |
|||
public: |
|||
static void drawAlarmCodePromptMessage( u8 numDigits ); |
|||
static void drawMaintenanceModeMessage(); |
|||
static void drawFillupConfirmationMessage(); |
|||
}; |
|||
|
|||
#endif // MAINTENANCE_SCREEN_H_
|
@ -0,0 +1,115 @@ |
|||
#include <Core/Utils/AsciiConverter.h> |
|||
|
|||
#include "VendingScreen.h" |
|||
#include "Gui.h" |
|||
|
|||
|
|||
static void drawMoneyValue( Gui::Font& font, Gui::CoordinateType posX, Gui::CoordinateType posY, u16 value ) |
|||
{ |
|||
Gui::Font::Text komma = GuiResources::getInstanceRef().fontArial20.text( "," ); |
|||
|
|||
redBlocks::Core::AsciiConverter::Decimal::StringRepresentation<u8> value1Str( value / 100 ); |
|||
redBlocks::Core::AsciiConverter::Decimal::StringRepresentation<u8> value2Str( value % 100 ); |
|||
// fill with leading 0s and skip the first 0, as we only need 2 digits
|
|||
value2Str.fill( '0' ); |
|||
Gui::Font::Text value1 = GuiResources::getInstanceRef().fontArial20.text( value1Str.getData() ); |
|||
Gui::Font::Text value2 = GuiResources::getInstanceRef().fontArial20.text( value2Str.getData() + 1 ); |
|||
|
|||
Gui::CoordinateType width = value1.getWidth() + komma.getWidth() + value2.getWidth(); |
|||
if ( posX > width ) |
|||
{ |
|||
posX -= width; |
|||
} |
|||
else |
|||
{ |
|||
posX = 0; |
|||
} |
|||
|
|||
Gui::paint( value1, Gui::LeftAlign( posX ), Gui::CenterVertical( posY ), GuiColorMap::FOREGROUND ); |
|||
posX += value1.getWidth(); |
|||
Gui::paint( komma, Gui::LeftAlign( posX ), Gui::CenterVertical( posY ), GuiColorMap::FOREGROUND ); |
|||
posX += komma.getWidth(); |
|||
Gui::paint( value2, Gui::LeftAlign( posX ), Gui::CenterVertical( posY ), GuiColorMap::FOREGROUND ); |
|||
} |
|||
|
|||
static void drawTwoLineMessage( const char* line1, const char* line2 ) |
|||
{ |
|||
Gui::clear( GuiColorMap::BACKGROUND ); |
|||
Gui::paint( GuiResources::getInstanceRef().fontArial20.text( line1 ), Gui::CenterHorizontal(), Gui::BottomAlign( Gui::Display::getHeight() / 2 ), GuiColorMap::FOREGROUND ); |
|||
Gui::paint( GuiResources::getInstanceRef().fontArial20.text( line2 ), Gui::CenterHorizontal(), Gui::TopAlign( Gui::Display::getHeight() / 2 ), GuiColorMap::FOREGROUND ); |
|||
Gui::update(); |
|||
} |
|||
|
|||
|
|||
void VendingScreen::drawPriceInfo( u16 price, u16 money ) |
|||
{ |
|||
const Gui::CoordinateType left = 15; |
|||
const Gui::CoordinateType right = Gui::Display::getWidth() - 15; |
|||
const Gui::CoordinateType firstLine = 5 + ( Gui::Display::getHeight() - 10 ) / 4; |
|||
const Gui::CoordinateType secondLine = 5 + ( ( Gui::Display::getHeight() - 10 ) / 4 ) * 3; |
|||
|
|||
Gui::clear( GuiColorMap::BACKGROUND ); |
|||
|
|||
if ( 0 == price ) |
|||
{ |
|||
Gui::paint( |
|||
GuiResources::getInstanceRef().fontArial20.text( "Select product" ), |
|||
Gui::CenterHorizontal(), |
|||
Gui::CenterVertical( firstLine ), |
|||
GuiColorMap::FOREGROUND |
|||
); |
|||
} |
|||
else |
|||
{ |
|||
Gui::paint( |
|||
GuiResources::getInstanceRef().fontArial20.text( "Price:" ), |
|||
Gui::LeftAlign( left ), |
|||
Gui::CenterVertical( firstLine ), |
|||
GuiColorMap::FOREGROUND |
|||
); |
|||
|
|||
drawMoneyValue( GuiResources::getInstanceRef().fontArial20, right, firstLine, price ); |
|||
} |
|||
|
|||
Gui::paint( |
|||
GuiResources::getInstanceRef().bitmaskCoins, |
|||
Gui::LeftAlign( left + 5 ), |
|||
Gui::CenterVertical( secondLine ), |
|||
GuiColorMap::FOREGROUND |
|||
); |
|||
drawMoneyValue( GuiResources::getInstanceRef().fontArial20, right, secondLine, money ); |
|||
|
|||
|
|||
Gui::update(); |
|||
} |
|||
|
|||
void VendingScreen::drawProductNotAvailableMessage() |
|||
{ |
|||
drawTwoLineMessage( "Not available!", "Select other" ); |
|||
} |
|||
|
|||
|
|||
void VendingScreen::drawProductErrorMessage() |
|||
{ |
|||
drawTwoLineMessage( "Error!", "Coins returned" ); |
|||
} |
|||
|
|||
void VendingScreen::drawReturningMoneyMessage() |
|||
{ |
|||
drawTwoLineMessage( "Your money", "is returned" ); |
|||
} |
|||
|
|||
void VendingScreen::drawReleaseMessage() |
|||
{ |
|||
drawTwoLineMessage( "Your product", "is released!" ); |
|||
} |
|||
|
|||
void VendingScreen::drawTakeProductMessage() |
|||
{ |
|||
drawTwoLineMessage( "Remove your", "product!" ); |
|||
} |
|||
|
|||
void VendingScreen::drawPrompt() |
|||
{ |
|||
drawTwoLineMessage( "Select a", "product!" ); |
|||
} |
@ -0,0 +1,21 @@ |
|||
#ifndef VENDING_SCREEN_H_ |
|||
#define VENDING_SCREEN_H_ |
|||
|
|||
#include <Core/Base/NoInstanceBase.h> |
|||
|
|||
/**
|
|||
* This class paints price and payment information to the graphical display. |
|||
*/ |
|||
class VendingScreen : public redBlocks::Core::NoInstanceBase |
|||
{ |
|||
public: |
|||
static void drawPriceInfo( u16 price, u16 money ); |
|||
static void drawProductNotAvailableMessage(); |
|||
static void drawProductErrorMessage(); |
|||
static void drawReturningMoneyMessage(); |
|||
static void drawReleaseMessage(); |
|||
static void drawTakeProductMessage(); |
|||
static void drawPrompt(); |
|||
}; |
|||
|
|||
#endif // VENDING_SCREEN_H_
|
@ -0,0 +1 @@ |
|||
#include <Memory/HeapManager/HeapManagerConfig-default.h> |
@ -0,0 +1,44 @@ |
|||
#ifndef PLATFORM_H_ |
|||
#define PLATFORM_H_ |
|||
|
|||
#include "LowLevelPlatform.h" |
|||
#include <Core/Log/TStandardLogger.h> |
|||
#include <HAL/TBufferedComInterfaceWriter.h> |
|||
#include <OS/MainLoop/TMainLoopScheduler.h> |
|||
#include <Drivers/TCoinDetectorDriver.h> |
|||
#include <Drivers/TGsmModemDriver.h> |
|||
|
|||
/**
|
|||
* This class enhances the low layer hardware abstraction with high level (and thus |
|||
* hardware independent) driver functionality. |
|||
*/ |
|||
class Platform : public LowLevelPlatform |
|||
{ |
|||
public: |
|||
typedef redBlocks::OS::TMainLoopScheduler<LowLevelPlatform::IsrLock, 1, 1, LowLevelPlatform::PowerSaveCallback> OS; |
|||
typedef redBlocks::HAL::TBufferedComInterfaceWriter<Platform::LogComInterface> BufferedLogComInterfaceWriter; |
|||
typedef redBlocks::Core::Log::TGlobalStandardLogger<Platform::BufferedLogComInterfaceWriter> StandardLogger; |
|||
typedef TCoinDetectorDriver<Platform::CoinDetectorComInterface, Platform::OS> CoinDetectorDriver; |
|||
typedef TGsmModemDriver<Platform::GsmModemComInterface> GsmModemDriver; |
|||
|
|||
static void initHighLevelDrivers() |
|||
{ |
|||
new BufferedLogComInterfaceWriter( 400 ); |
|||
new StandardLogger(); |
|||
new CoinDetectorDriver(); |
|||
new GsmModemDriver(); |
|||
} |
|||
}; |
|||
|
|||
// callback routing from low level drivers to high level drivers
|
|||
RB_CONNECT_ISR_CBK( Platform::SystemTickDriver, Platform::SystemTickDriver::CBK_ON_SYSTEM_TICK, Platform::OS::tick() ) |
|||
RB_CONNECT_ISR_CBK( Platform::LogComInterface, Platform::LogComInterface::CBK_ON_RECV_DATA, /** Empty */ ) |
|||
RB_CONNECT_ISR_CBK( Platform::LogComInterface, Platform::LogComInterface::CBK_ON_SEND_READY, Platform::BufferedLogComInterfaceWriter::onSendReadyCallback() ) |
|||
RB_CONNECT_ISR_CBK( Platform::CoinDetectorComInterface, Platform::CoinDetectorComInterface::CBK_ON_RECV_DATA, Platform::CoinDetectorDriver::getInstanceRef().onCoinDetectorEvent() ) |
|||
RB_CONNECT_ISR_CBK( Platform::CoinDetectorComInterface, Platform::CoinDetectorComInterface::CBK_ON_SEND_READY, /** Empty */ ) |
|||
RB_CONNECT_ISR_CBK( Platform::GsmModemComInterface, Platform::GsmModemComInterface::CBK_ON_RECV_DATA, /** Empty */ ) |
|||
RB_CONNECT_ISR_CBK( Platform::GsmModemComInterface, Platform::GsmModemComInterface::CBK_ON_SEND_READY, Platform::GsmModemDriver::onSendReadyCallback() ) |
|||
RB_CONNECT_ISR_CBK( Platform::ConfigurationComInterface, Platform::ConfigurationComInterface::CBK_ON_RECV_DATA, /** Empty */ ) |
|||
RB_CONNECT_ISR_CBK( Platform::ConfigurationComInterface, Platform::ConfigurationComInterface::CBK_ON_SEND_READY, /** Empty */ ) |
|||
|
|||
#endif // PLATFORM_H_
|
@ -0,0 +1,25 @@ |
|||
#ifndef PLATFORM_CALLBACKS_H_ |
|||
#define PLATFORM_CALLBACKS_H_ |
|||
|
|||
#include <Application/Application.h> |
|||
#include <Platform.h> |
|||
|
|||
extern "C" void onStartPressed( void ); |
|||
|
|||
|
|||
// callback routing from platform to application modules
|
|||
RB_CONNECT_ISR_CBK( Platform::TemperatureSensor, Platform::TemperatureSensor::CBK_ON_SAMPLING_FINISHED, Application::getInstanceRef().getTemperatureController().onTemperatureAvailable() ) |
|||
RB_CONNECT_ISR_CBK( Platform::PowerSupervision, Platform::PowerSupervision::CBK_ON_INPUT_CHANGED, /** Empty */ ) |
|||
RB_CONNECT_ISR_CBK( Platform::FrontDoorProtection, Platform::FrontDoorProtection::CBK_ON_INPUT_CHANGED, Application::getGlobalState().onFrontDoorContactChange() ) |
|||
RB_CONNECT_ISR_CBK( Platform::ReturnMoneyButton, Platform::ReturnMoneyButton::CBK_ON_INPUT_CHANGED, Application::getVendingMode().onReleaseMoneyBtnPressed() ) |
|||
RB_CONNECT_ISR_CBK( Platform::Product1Button, Platform::Product1Button::CBK_ON_INPUT_CHANGED, Application::getVendingMode().onProductBtnPressed( 0 ) ) |
|||
RB_CONNECT_ISR_CBK( Platform::Product2Button, Platform::Product2Button::CBK_ON_INPUT_CHANGED, Application::getVendingMode().onProductBtnPressed( 1 ) ) |
|||
RB_CONNECT_ISR_CBK( Platform::Product3Button, Platform::Product3Button::CBK_ON_INPUT_CHANGED, Application::getVendingMode().onProductBtnPressed( 2 ) ) |
|||
RB_CONNECT_ISR_CBK( Platform::Product4Button, Platform::Product4Button::CBK_ON_INPUT_CHANGED, Application::getVendingMode().onProductBtnPressed( 3 ) ) |
|||
RB_CONNECT_ISR_CBK( Platform::LightBarrier, Platform::LightBarrier::CBK_ON_INPUT_CHANGED, Application::getVendingMode().onLightBarrierEvent() ) |
|||
RB_CONNECT_ISR_CBK( Platform::FilledUpButton, Platform::FilledUpButton::CBK_ON_INPUT_CHANGED, Application::getVendingMode().onFillupBtnPressed() ) |
|||
RB_CONNECT_ISR_CBK( Platform::Keypad, Platform::Keypad::CBK_ON_KEY_PRESSED, Application::getMaintenanceMode().onKeyPressed( Platform::Keypad::getKey() ) ) |
|||
RB_CONNECT_ISR_CBK( Platform::StartButton, Platform::StartButton::CBK_ON_INPUT_CHANGED, onStartPressed() ) |
|||
|
|||
|
|||
#endif // PLATFORM_CALLBACKS_H_
|
@ -0,0 +1,18 @@ |
|||
//RB_PROC:ALL:HEADER_DATA
|
|||
|
|||
#ifndef RB_CONFIG_H_ |
|||
#define RB_CONFIG_H_ |
|||
|
|||
// switch logging on, if not otherwise specified via compiler switch
|
|||
#ifndef RB_LOG_ON |
|||
#define RB_LOG_ON 1 |
|||
#endif |
|||
|
|||
// the output of logging locations is deactivated, because otherwise the resulting binary size exceed the
|
|||
// maximum allowed linker size of 32kb in the uVision evaluation version
|
|||
#define RB_LOG_LOCATION_ON 0 |
|||
|
|||
// add project specific configuration options before this include directive
|
|||
#include <rbConfig-default.h> |
|||
|
|||
#endif //RB_CONFIG_H_
|
Some files were not shown because too many files changed in this diff
Loading…
Reference in new issue